Compare commits
49 Commits
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
7111494545 | ||
|
|
2833a6cfb1 | ||
|
|
e9dc3ff867 | ||
|
|
ca8856d77c | ||
|
|
2a4cc75f0a | ||
|
|
486cccd1da | ||
|
|
4a93f3e147 | ||
|
|
64871efe6d | ||
|
|
3e382a42e1 | ||
|
|
ff973beb32 | ||
|
|
ced9908da5 | ||
|
|
ea52f821c5 | ||
|
|
cf2b32c66d | ||
|
|
462da5b99b | ||
|
|
9b481ba8ef | ||
|
|
557bb9cc6a | ||
|
|
2cc06be317 | ||
|
|
0afd2b4b8c | ||
|
|
818e5cf255 | ||
|
|
1978274686 | ||
|
|
9c95e154c1 | ||
|
|
4f912a7063 | ||
|
|
45cc57058c | ||
|
|
d222ed2dd1 | ||
|
|
fba53984eb | ||
|
|
b810c4b0bf | ||
|
|
6d5a4ad759 | ||
|
|
802521b364 | ||
|
|
466aecb4b8 | ||
|
|
c34f31c869 | ||
|
|
5a1348868e | ||
|
|
45e244f10c | ||
|
|
9b38dd7d74 | ||
|
|
7d1098740b | ||
|
|
b3ff824806 | ||
|
|
db889f217d | ||
|
|
e60ca05e64 | ||
|
|
1831a9b286 | ||
|
|
f3939938b4 | ||
|
|
2c8b07b1cb | ||
|
|
2ef11d5eea | ||
|
|
5d2c618553 | ||
|
|
917c2d82c7 | ||
|
|
8590d8243c | ||
|
|
bc1ddca4f0 | ||
|
|
d4bda0a45d | ||
|
|
6a49176c0e | ||
|
|
bfd44ada12 | ||
|
|
5172135014 |
66
CHANGELOG.md
66
CHANGELOG.md
@@ -1,5 +1,71 @@
|
||||
# ZeroBrane Studio Changelog
|
||||
|
||||
## v0.35 (Feb 10 2013)
|
||||
|
||||
### Highlights
|
||||
- Added support for **debugging Lua 5.2 scripts**.
|
||||
- Added support for **cross-platform remote debugging**.
|
||||
- Added support for starting Gideros **on-device debugging**.
|
||||
- Added support for live coding, script reloading, and coroutine debugging under LuaJIT.
|
||||
- Added **Marmalade Quick** support.
|
||||
- Added **live-coding for Corona** interpreter.
|
||||
- Added editor tab popup menu with 'Close All', 'Close Other', and other items.
|
||||
|
||||
### Special thanks
|
||||
- To Roland Yonaba and Fringale for updates to French translation.
|
||||
- To Fringale for enhanced line-endings handling.
|
||||
- To toiffel for build improvements, continuous work on wxwidgets 2.9 support, and several patches.
|
||||
- To Andy Bower for the stream of feedback on live coding and on-device debugging.
|
||||
|
||||
### Improvements
|
||||
- Added `debugger.runonstart` option to configure if debugging should run immediately after starting.
|
||||
- Added `editor.checkeol` option to configure checking for eol encoding in loaded files.
|
||||
- Added Marmalade Quick support.
|
||||
- Added support for starting Gideros on-device debugging.
|
||||
- Added requesting user attention when stopped during debugging.
|
||||
- Added example for `defaulteol` configuration option.
|
||||
- Added configuration option for compact folding (`editor.`).
|
||||
- Added support for cross-platform remote debugging.
|
||||
- Added support for script reloading and coroutine debugging under LuaJIT (MobDebug 0.514).
|
||||
- Added Russian translation for new messages.
|
||||
- Added handling of malformed UTF8 characters in files (fixes #97).
|
||||
- Added support for debugging Lua 5.2 scripts.
|
||||
- Added workaround for Moai require path issue (fixes #96; fixes #87).
|
||||
- Added editor tab popup menu with 'Close All', 'Close Other', and other items.
|
||||
- Added C/CPP specification file and a configuration example.
|
||||
- Added XCode-like key mapping.
|
||||
- Added removing of file: prefix and url decoding of filepaths (helps #89).
|
||||
- Added a workaround for returning incorrect project folder (helps #89).
|
||||
- Adjusted handling of filepath to work with relative and absolute paths (helps #89).
|
||||
- Enabled live-coding for Corona interpreter.
|
||||
- Improved line-endings handling (Fringale).
|
||||
- Improved reporting of stack and serialization run-time errors.
|
||||
- Updated Gideros interpreter to run debugging immediately after starting; Use `debugger.runonstart = false` to disable.
|
||||
- Updated Linux startup script to use online versions of wxlua packages (deb files).
|
||||
- Updated handling of file: prefix as it's different on Windows and OSX (helps #89).
|
||||
- Updated messages in the starter script.
|
||||
- Updated function call parsing to recognize "func{}" and "func''" syntax.
|
||||
- Updated os.exit() call in local console to exit gracefully.
|
||||
- Updated French translation with various fixes and tweaks (Fringale).
|
||||
- Updated French translation with newly added strings (Fringale).
|
||||
- Updated 'Close page' and its translations.
|
||||
- Updated configuration examples and documentation (helps #55).
|
||||
- Updated the size of the function list dropdown on Windows (helps #89).
|
||||
- Typos fixes, small changes in French translation (Roland Yonaba).
|
||||
|
||||
### Incompatibilities
|
||||
- Gideros debugging is changed to start immediately; use `debugger.runonstart = false` to disable.
|
||||
- Removed mosync support from the debugger into a separate module.
|
||||
- Added mixed end-of-line reporting; use `editor.checkeol = false` to disable.
|
||||
- Added reporting of malformed UTF-8.
|
||||
|
||||
### Fixes
|
||||
- Fixed a rare crash on OSX when closing IDE with an application running under debugger.
|
||||
- Fixed path handling for metalua to avoid conflicts with other modules that may include lexer.lua file.
|
||||
- Fixed executing commands in the Remote console immediately after `mobdebug.start()` (closes #100).
|
||||
- Fixed invalid escape sequence that fails under LuaJIT.
|
||||
- Fixed an issue with spec files when a separator (sep) is not specified.
|
||||
|
||||
## v0.34 (Dec 12 2012)
|
||||
|
||||
### Highlights
|
||||
|
||||
@@ -821,7 +821,7 @@ return {
|
||||
},
|
||||
seek = {
|
||||
type = "function",
|
||||
description = "Sets and gets the file position, measured from the beginning of the file, to the position given by offset plus a base specified by the string whence.\n\nThe string whence is specified as follows:\n\n* \"set\": base is position 0 (beginning of the file);\n\n* \"cur\": base is current position;\n\n* \"end\": base is end of file.\n\nIn case of success, seek returns the final file position, measured in bytes from the beginning of the file. If seek fails, it returns nil, plus a string describing the error.\n\The default value for whence is \"cur\", and for offset is 0. Therefore, the call file:seek() returns the current file position, without changing it; the call file:seek(\"set\") sets the position to the beginning of the file (and returns 0); and the call file:seek(\"end\") sets the position to the end of the file, and returns its size.",
|
||||
description = "Sets and gets the file position, measured from the beginning of the file, to the position given by offset plus a base specified by the string whence.\n\nThe string whence is specified as follows:\n\n* \"set\": base is position 0 (beginning of the file);\n\n* \"cur\": base is current position;\n\n* \"end\": base is end of file.\n\nIn case of success, seek returns the final file position, measured in bytes from the beginning of the file. If seek fails, it returns nil, plus a string describing the error.\n\nThe default value for whence is \"cur\", and for offset is 0. Therefore, the call file:seek() returns the current file position, without changing it; the call file:seek(\"set\") sets the position to the beginning of the file (and returns 0); and the call file:seek(\"end\") sets the position to the end of the file, and returns its size.",
|
||||
args = "(file: file, [whence: string [, offset: number]])",
|
||||
returns = "(number|nil [, string])",
|
||||
},
|
||||
|
||||
1244
api/lua/corona.lua
1244
api/lua/corona.lua
File diff suppressed because it is too large
Load Diff
@@ -1,4 +1,10 @@
|
||||
#!/bin/bash
|
||||
|
||||
sudo apt-get install gdebi
|
||||
sudo gdebi wxlua*.deb
|
||||
echo "Installing wxlua modules from ZeroBrane Studio repository..."
|
||||
sudo add-apt-repository ppa:zerobranestudio/zerobranestudio
|
||||
sudo apt-get update
|
||||
sudo apt-get install wxlua28
|
||||
|
||||
# To remove wxlua and required packages use:
|
||||
# sudo apt-get purge wxlua28
|
||||
# sudo apt-get autoremove
|
||||
|
||||
@@ -24,7 +24,6 @@ typedef void varfuncvoid (void *L,...);
|
||||
// from lua.h
|
||||
#define LUA_GLOBALSINDEX (-10002)
|
||||
|
||||
|
||||
static voidfunc *luaL_newstate;
|
||||
static varfunc *luaL_loadbuffer;
|
||||
static varfunc *luaL_openlibs;
|
||||
@@ -146,13 +145,12 @@ int main (int argc, char *argv[])
|
||||
#endif
|
||||
HINSTANCE hinstLib;
|
||||
|
||||
|
||||
char buffer[MAX_PATH],*file;
|
||||
|
||||
if (!GetFullPathName(argv[0],MAX_PATH,buffer,&file)) {
|
||||
MessageBox(NULL,
|
||||
TEXT("Couldn't find the correct working directory"),
|
||||
TEXT("Failed to start estrela"),
|
||||
TEXT("Failed to start editor"),
|
||||
MB_OK|MB_ICONERROR);
|
||||
return 0;
|
||||
}
|
||||
@@ -207,18 +205,18 @@ int main (int argc, char *argv[])
|
||||
else
|
||||
MessageBox(NULL,
|
||||
TEXT("An unexpected error occured while loading the lua chunk."),
|
||||
TEXT("Failed to start estrela"),
|
||||
TEXT("Failed to start editor"),
|
||||
MB_OK|MB_ICONERROR);
|
||||
} else
|
||||
MessageBox(NULL,
|
||||
TEXT("Couldn't initialize a luastate"),
|
||||
TEXT("Failed to start estrela"),
|
||||
TEXT("Failed to start editor"),
|
||||
MB_OK|MB_ICONERROR);
|
||||
} else {
|
||||
MessageBox(NULL,
|
||||
TEXT("Could not load all functions that are supposed to be located in the lua5.1.dll\n"
|
||||
"This is not supposed to be happening..."),
|
||||
TEXT("Failed to start estrela"),
|
||||
TEXT("Failed to start editor"),
|
||||
MB_OK|MB_ICONERROR);
|
||||
}
|
||||
|
||||
@@ -227,10 +225,9 @@ int main (int argc, char *argv[])
|
||||
} else {
|
||||
MessageBox(NULL,
|
||||
TEXT("The lua5.1.dll could not be found or loaded, please check the working directory of the application.\n"),
|
||||
TEXT("Failed to initialize estrela"),
|
||||
TEXT("Failed to initialize editor"),
|
||||
MB_OK|MB_ICONERROR);
|
||||
}
|
||||
|
||||
|
||||
return 0;
|
||||
}
|
||||
|
||||
Binary file not shown.
@@ -6,7 +6,7 @@ return {
|
||||
["&About"] = "&Acerca de...", -- src\editor\menu_help.lua
|
||||
["&Add Watch"] = "Añadir observación", -- src\editor\debugger.lua
|
||||
["&Break"] = "Ruptura", -- src\editor\menu_project.lua
|
||||
["&Close page"] = "Cerrar página", -- src\editor\menu_file.lua
|
||||
["&Close Page"] = "Cerrar página", -- src\editor\menu_file.lua
|
||||
["&Compile"] = "Compilar", -- src\editor\menu_project.lua
|
||||
["&Copy"] = "Copiar", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Default Layout"] = "Diseño por defecto", -- src\editor\menu_view.lua
|
||||
|
||||
270
cfg/i18n/fr.lua
270
cfg/i18n/fr.lua
@@ -1,190 +1,200 @@
|
||||
return {
|
||||
[0] = function(c) return c == 1 and 1 or 2 end, -- plural
|
||||
["&About"] = "&A propos", -- src\editor\menu_help.lua
|
||||
["&Add Watch"] = "Ajouter un point d'observation", -- src\editor\debugger.lua
|
||||
["&Break"] = "Interrompre", -- src\editor\menu_project.lua
|
||||
["&Close page"] = "Fermer la page", -- src\editor\menu_file.lua
|
||||
["&Compile"] = "Compiler", -- src\editor\menu_project.lua
|
||||
["&Copy"] = "Copier", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Default Layout"] = "Affichage par défaut", -- src\editor\menu_view.lua
|
||||
["&Edit Watch"] = "Editer le point d'observation", -- src\editor\debugger.lua
|
||||
["&Edit"] = "Editer", -- src\editor\menu_edit.lua
|
||||
["&File"] = "Fichier", -- src\editor\menu_file.lua
|
||||
["&Find"] = "Trouver", -- src\editor\menu_search.lua
|
||||
["&Fold/Unfold All"] = "Replier/Déplier tout", -- src\editor\menu_edit.lua
|
||||
["&Goto Line"] = "Aller à la ligne", -- src\editor\menu_search.lua
|
||||
["&Help"] = "Aide", -- src\editor\menu_help.lua
|
||||
["&About"] = "À &propos", -- src\editor\menu_help.lua
|
||||
["&Add Watch"] = "&Ajouter une expression", -- src\editor\debugger.lua
|
||||
["&Break"] = "&Interrompre", -- src\editor\menu_project.lua
|
||||
["&Close Page"] = "&Fermer la page", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["&Compile"] = "&Compiler", -- src\editor\menu_project.lua
|
||||
["&Copy"] = "Co&pier", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Default Layout"] = "Affichage par &défaut", -- src\editor\menu_view.lua
|
||||
["&Edit Watch"] = "&Modifier une expression", -- src\editor\debugger.lua
|
||||
["&Edit"] = "É&dition", -- src\editor\menu_edit.lua
|
||||
["&File"] = "&Fichier", -- src\editor\menu_file.lua
|
||||
["&Find"] = "&Rechercher...", -- src\editor\menu_search.lua
|
||||
["&Fold/Unfold All"] = "Re&plier/Déplier tout", -- src\editor\menu_edit.lua
|
||||
["&Goto Line"] = "&Aller à la ligne...", -- src\editor\menu_search.lua
|
||||
["&Help"] = "Aid&e", -- src\editor\menu_help.lua
|
||||
["&New"] = "&Nouveau", -- src\editor\menu_file.lua
|
||||
["&Open..."] = "&Ouvrir", -- src\editor\menu_file.lua
|
||||
["&Output/Console Window"] = "Sortie/Console", -- src\editor\menu_view.lua
|
||||
["&Paste"] = "Coller", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Project"] = "Projet", -- src\editor\menu_project.lua, src\editor\inspect.lua
|
||||
["&Redo"] = "Répéter", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Remove Watch"] = "Supprimer le point d'observation", -- src\editor\debugger.lua
|
||||
["&Replace"] = "Remplacer", -- src\editor\menu_search.lua
|
||||
["&Run"] = "Exécuter", -- src\editor\menu_project.lua
|
||||
["&Save"] = "Enregister", -- src\editor\menu_file.lua
|
||||
["&Search"] = "Rechercher", -- src\editor\menu_search.lua
|
||||
["&Sort"] = "Trier", -- src\editor\menu_search.lua
|
||||
["&Stack Window"] = "Pile d'exécution", -- src\editor\menu_view.lua
|
||||
["&Start Debugger Server"] = "Lancer le débogueur", -- src\editor\menu_project.lua
|
||||
["&Undo"] = "Défaire", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&View"] = "Vue", -- src\editor\menu_view.lua
|
||||
["&Watch Window"] = "Fenêtre d'observation", -- src\editor\menu_view.lua
|
||||
["&Watches"] = "Points d'observation", -- src\editor\debugger.lua
|
||||
["About ZeroBrane Studio"] = "A propos de ZeroBrane Studio", -- src\editor\menu_help.lua
|
||||
["&Open..."] = "&Ouvrir...", -- src\editor\menu_file.lua
|
||||
["&Output/Console Window"] = "&Sortie/Console", -- src\editor\menu_view.lua
|
||||
["&Paste"] = "Co&ller", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Project"] = "&Projet", -- src\editor\menu_project.lua, src\editor\inspect.lua
|
||||
["&Redo"] = "&Rétablir", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Remove Watch"] = "&Supprimer une expression", -- src\editor\debugger.lua
|
||||
["&Replace"] = "Re&mplacer...", -- src\editor\menu_search.lua
|
||||
["&Run"] = "&Exécuter", -- src\editor\menu_project.lua
|
||||
["&Save"] = "&Enregistrer", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["&Search"] = "&Recherche", -- src\editor\menu_search.lua
|
||||
["&Sort"] = "&Trier", -- src\editor\menu_search.lua
|
||||
["&Stack Window"] = "&Pile d'exécution", -- src\editor\menu_view.lua
|
||||
["&Start Debugger Server"] = "Lancer le &serveur de débogage", -- src\editor\menu_project.lua
|
||||
["&Undo"] = "&Annuler", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&View"] = "&Affichage", -- src\editor\menu_view.lua
|
||||
["&Watch Window"] = "&Expressions espionnes", -- src\editor\menu_view.lua
|
||||
["&Watches"] = "&Expressions", -- src\editor\debugger.lua
|
||||
["About ZeroBrane Studio"] = "À propos de ZeroBrane Studio", -- src\editor\menu_help.lua
|
||||
["Add Watch Expression"] = "Ajouter une expression", -- src\editor\editor.lua
|
||||
["Add to Scratchpad"] = "Ajouter au brouillon", -- src\editor\editor.lua
|
||||
["All files"] = "Tous les fichiers", -- src\editor\commands.lua
|
||||
["Allow external process to start debugging"] = "Autoriser aux processus externes le démarrage du débogueur", -- src\editor\menu_project.lua
|
||||
["Allow external process to start debugging"] = "Autoriser les processus externes à lancer le débogage", -- src\editor\menu_project.lua
|
||||
["Analyze the source code"] = "Analyser le code source", -- src\editor\inspect.lua
|
||||
["Analyze"] = "Analyser", -- src\editor\inspect.lua
|
||||
["Auto Complete Identifiers"] = "Identificateur d'auto-complétion", -- src\editor\menu_edit.lua
|
||||
["Auto complete while typing"] = "Auto-complémention en mode saisie", -- src\editor\menu_edit.lua
|
||||
["Auto Complete Identifiers"] = "Auto-compléter les identifiants", -- src\editor\menu_edit.lua
|
||||
["Auto complete while typing"] = "Auto-compléter lors de la saisie", -- src\editor\menu_edit.lua
|
||||
["Break execution at the next executed line of code"] = "Interrompre l'exécution à la ligne suivante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["C&lear Output Window"] = "Effacer la sortie console", -- src\editor\menu_project.lua
|
||||
["C&omment/Uncomment"] = "Commenter/Décommenter", -- src\editor\menu_edit.lua
|
||||
["Can't debug the script in the active editor window."] = "Impossible de déboguer le script dans la fenêtre d'édition active", -- src\editor\debugger.lua
|
||||
["Can't find file '%s' in the current project to activate for debugging. Update the project or open the file in the editor before debugging."] = "Fichier '%s' non trouvé dans le projet en cours pour le débogage. Mettez le projet à jour ou ouvrez le fichier dans l'éditeur avant débogage.", -- src\editor\debugger.lua
|
||||
["Can't process auto-recovery record; invalid format: %s."] = "Impossible de restaurer automatiquement l'enregistrement; Format invalide: %s.", -- src\editor\commands.lua
|
||||
["Can't run the entry point script ('%s')."] = "Impossible d'exécuter le point d'entrée du script (%s).", -- src\editor\debugger.lua
|
||||
["Can't start debugging session due to internal error '%s'."] = "Impossible de démarrer la session de débogage: erreur interne '%s'.'", -- src\editor\debugger.lua
|
||||
["Can't start debugging without an opened file or with the current file not being saved ('%s')."] = "Impossible de déboguer sans fichier ouvert ou si le fichier en cours d'édition n'a pas été enregistré ('%s').", -- src\editor\debugger.lua
|
||||
["C&lear Output Window"] = "E&ffacer la fenêtre de sortie", -- src\editor\menu_project.lua
|
||||
["C&omment/Uncomment"] = "Co&mmenter/Décommenter", -- src\editor\menu_edit.lua
|
||||
["Can't debug the script in the active editor window."] = "Impossible de déboguer le script dans la fenêtre d'édition active.", -- src\editor\debugger.lua
|
||||
["Can't find file '%s' in the current project to activate for debugging. Update the project or open the file in the editor before debugging."] = "Impossible de trouver le fichier '%s' dans le projet courant pour permettre le débogage. Mettez le projet à jour ou ouvrez le fichier dans l'éditeur avant débogage.", -- src\editor\debugger.lua
|
||||
["Can't process auto-recovery record; invalid format: %s."] = "Impossible de lire la récupération automatique ; format invalide : %s.", -- src\editor\commands.lua
|
||||
["Can't run the entry point script ('%s')."] = "Impossible d'exécuter le point d'entrée du script ('%s').", -- src\editor\debugger.lua
|
||||
["Can't start debugging session due to internal error '%s'."] = "Impossible de lancer la session de débogage : erreur interne '%s'.", -- src\editor\debugger.lua
|
||||
["Can't start debugging without an opened file or with the current file not being saved ('%s')."] = "Impossible de lancer le débogage si aucun fichier n'est ouvert ou si le fichier courant n'a pas été enregistré ('%s').", -- src\editor\debugger.lua
|
||||
["Choose ..."] = "Choisir...", -- src\editor\menu_project.lua
|
||||
["Choose a project directory"] = "Choisissez un répertoire de projet", -- src\editor\menu_project.lua
|
||||
["Clear &Dynamic Words"] = "Effacer les mots dynamiques", -- src\editor\menu_edit.lua
|
||||
["Clear the output window before compiling or debugging"] = "Nettoyer la fenêtre de sortie avant compilation ou débogage", -- src\editor\menu_project.lua
|
||||
["Clear &Dynamic Words"] = "Effacer les mots &dynamiques", -- src\editor\menu_edit.lua
|
||||
["Clear the output window before compiling or debugging"] = "Effacer la fenêtre de sortie avant compilation ou débogage", -- src\editor\menu_project.lua
|
||||
["Close &Other Pages"] = "Fermer les &autres pages", -- src\editor\gui.lua
|
||||
["Close A&ll Pages"] = "Fermer &toutes les pages", -- src\editor\gui.lua
|
||||
["Close the current editor window"] = "Fermer la fenêtre d'édition active", -- src\editor\menu_file.lua
|
||||
["Co&ntinue"] = "Continuer", -- src\editor\menu_project.lua
|
||||
["Col: %d"] = "Col: %d", -- src\editor\editor.lua
|
||||
["Comment or uncomment current or selected lines"] = "Commenter/Décommenter les lignes actives (sélectionnées)", -- src\editor\menu_edit.lua
|
||||
["Co&ntinue"] = "Co&ntinuer", -- src\editor\menu_project.lua
|
||||
["Col: %d"] = "Col : %d", -- src\editor\editor.lua
|
||||
["Comment or uncomment current or selected lines"] = "Commenter ou décommenter les lignes courantes ou sélectionnées", -- src\editor\menu_edit.lua
|
||||
["Compilation error"] = "Erreur de commpilation", -- src\editor\debugger.lua, src\editor\commands.lua
|
||||
["Compilation successful; %.0f%% success rate (%d/%d)."] = "Compilation réussie; taux de succès : %.0f%% (%d/%d).", -- src\editor\commands.lua
|
||||
["Compilation successful; %.0f%% success rate (%d/%d)."] = "Compilation réussie ; taux de succès : %.0f%% (%d/%d).", -- src\editor\commands.lua
|
||||
["Compile the current file"] = "Сompiler le fichier courant", -- src\editor\menu_project.lua
|
||||
["Complete &Identifier"] = "Complétion d'identificateur", -- src\editor\menu_edit.lua
|
||||
["Complete the current identifier"] = "Complétion de l'identificateur courant", -- src\editor\menu_edit.lua
|
||||
["Complete &Identifier"] = "Compléter l'&identifiant", -- src\editor\menu_edit.lua
|
||||
["Complete the current identifier"] = "Compléter l'identifiant courant", -- src\editor\menu_edit.lua
|
||||
["Copy selected text to clipboard"] = "Copier le texte sélectionné dans le presse-papiers", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Couldn't activate file '%s' for debugging; continuing without it."] = "Echec d'activation du fichier '%s' pour débogage; Poursuite du processus en ignorant le fichier.", -- src\editor\debugger.lua
|
||||
["Couldn't activate file '%s' for debugging; continuing without it."] = "Impossible d'activer le fichier '%s' pour débogage ; poursuite du processus en ignorant le fichier.", -- src\editor\debugger.lua
|
||||
["Create an empty document"] = "Créer un document vierge", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Cu&t"] = "Couper", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["Cu&t"] = "&Couper", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["Cut selected text to clipboard"] = "Couper le texte selectionné et copier dans le presse-papiers", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Debugger server started at %s:%d."] = "Débogueur démarré à %s:%s", -- src\editor\debugger.lua
|
||||
["Debugger server started at %s:%d."] = "Serveur de débogage démarré à %s:%d.", -- src\editor\debugger.lua
|
||||
["Debugging session completed (%s)."] = "Session de débogage terminée (%s).", -- src\editor\debugger.lua
|
||||
["Debugging session started in '%s'."] = "Session de débogage démarrée dans '%s'.", -- src\editor\debugger.lua
|
||||
["Do you want to reload it?"] = "Voulez -vous le charger à nouveau?", -- src\editor\editor.lua
|
||||
["Do you want to save the changes to '%s'?"] = "Voulez-vous sauvegarder les changements dans '%s'?", -- src\editor\commands.lua
|
||||
["E&xit"] = "Sortie", -- src\editor\menu_file.lua
|
||||
["Enter Lua code and press Enter to run it."] = "Entrer du code Lua et pressez <Entrée> pour l`exécuter.", -- src\editor\shellbox.lua
|
||||
["Debugging suspended at %s:%s (couldn't activate the file)."] = "Débogage interrompu à %s:%s (impossible d'activer le fichier).", -- src\editor\debugger.lua
|
||||
["Do you want to reload it?"] = "Voulez-vous le recharger ?", -- src\editor\editor.lua
|
||||
["Do you want to save the changes to '%s'?"] = "Voulez-vous enregistrer les modifications dans '%s' ?", -- src\editor\commands.lua
|
||||
["E&xit"] = "&Quitter", -- src\editor\menu_file.lua
|
||||
["Enter Lua code and press Enter to run it."] = "Saisissez du code Lua et appuyez sur <Entrée> pour l´exécuter.", -- src\editor\shellbox.lua
|
||||
["Enter line number"] = "Entrez le numéro de ligne", -- src\editor\menu_search.lua
|
||||
["Error while loading API file: %s"] = "Erreur lors du chargement du fichier d'API: %s", -- src\editor\autocomplete.lua
|
||||
["Error while processing API file: %s"] = "Erreur lors de la lecture du fichier d'API: %s", -- src\editor\autocomplete.lua
|
||||
["Error while loading API file: %s"] = "Erreur lors du chargement du fichier d'API : %s", -- src\editor\autocomplete.lua
|
||||
["Error while loading configuration file: %s"] = "Erreur lors du chargement du fichier de configuration : %s", -- src\editor\style.lua
|
||||
["Error while processing API file: %s"] = "Erreur lors de la lecture du fichier d'API : %s", -- src\editor\autocomplete.lua
|
||||
["Error while processing configuration file: %s"] = "Erreur lors de la lecture du fichier de configuration : %s", -- src\editor\style.lua
|
||||
["Error"] = "Erreur", -- src\editor\commands.lua
|
||||
["Evaluate &Watches"] = "Evaluer les points d'observation", -- src\editor\debugger.lua
|
||||
["Evaluate in Console"] = "Evaluer en console", -- src\editor\editor.lua
|
||||
["Evaluate &Watches"] = "&Evaluer les expressions", -- src\editor\debugger.lua
|
||||
["Evaluate in Console"] = "Evaluer dans la console", -- src\editor\editor.lua
|
||||
["Execute the current project/file and keep updating the code to see immediate results"] = "Exécuter le projet/fichier courant en mettant le code à jour afin de voir les résultats en temps réel", -- src\editor\menu_project.lua
|
||||
["Execute the current project/file"] = "Exécuter le projet/fichier courant", -- src\editor\menu_project.lua
|
||||
["Execution error"] = "Erreur d'exécution", -- src\editor\debugger.lua
|
||||
["Exit program"] = "Sortie du programme", -- src\editor\menu_file.lua
|
||||
["Exit program"] = "Quitter le programme", -- src\editor\menu_file.lua
|
||||
["Expr"] = "Expr.", -- src\editor\debugger.lua
|
||||
["Expression"] = "Expresseion", -- src\editor\debugger.lua
|
||||
["Expression"] = "Expression", -- src\editor\debugger.lua
|
||||
["File '%s' has been modified on disk."] = "Le fichier '%s' a été modifié sur le disque.", -- src\editor\editor.lua
|
||||
["File '%s' has more recent timestamp than restored '%s'; please review before saving."] = "Le fichier '%s' a un horodatage plus récent que celui restauré '%s'; veuillez vérifier avant enregistrement.", -- src\editor\commands.lua
|
||||
["File '%s' has more recent timestamp than restored '%s'; please review before saving."] = "Le fichier '%s' a un horodatage plus récent que celui restauré '%s' ; veuillez vérifier avant d'enregistrer.", -- src\editor\commands.lua
|
||||
["File '%s' no longer exists."] = "Le fichier '%s' n'existe plus.", -- src\editor\editor.lua
|
||||
["File history"] = "Historique de fichier", -- src\editor\menu_file.lua
|
||||
["Find &In Files"] = "Rechercher dans les fichiers", -- src\editor\menu_search.lua
|
||||
["Find &Next"] = "Rechercher l'occurence suivante", -- src\editor\menu_search.lua
|
||||
["Find &Previous"] = "Rechercher l'occurence précédente", -- src\editor\menu_search.lua
|
||||
["Find &In Files"] = "Rec&hercher dans les fichiers...", -- src\editor\menu_search.lua
|
||||
["Find &Next"] = "Rechercher l'occurence &suivante", -- src\editor\menu_search.lua
|
||||
["Find &Previous"] = "Rechercher l'occurence &précédente", -- src\editor\menu_search.lua
|
||||
["Find and replace text in files"] = "Rechercher et remplacer le texte dans les fichiers", -- src\editor\menu_search.lua
|
||||
["Find and replace text"] = "Rechercher et remplacer le texte", -- src\editor\menu_search.lua, src\editor\gui.lua
|
||||
["Find text in files"] = "Rechercher le texte dans les fichiers", -- src\editor\menu_search.lua
|
||||
["Find text"] = "Rechercher le texte", -- src\editor\menu_search.lua, src\editor\gui.lua
|
||||
["Find the earlier text occurence"] = "Recherche l'occurence précédente du texte", -- src\editor\menu_search.lua
|
||||
["Find the next text occurrence"] = "Recherche l'occurence suivante du texte", -- src\editor\menu_search.lua
|
||||
["Fold or unfold all code folds"] = "Replier/Déplier tous les blocs de code repliés", -- src\editor\menu_edit.lua
|
||||
["Found auto-recovery record and restored saved session."] = "Enregistrement automatique trouvé et session restaurée", -- src\editor\commands.lua
|
||||
["Full &Screen"] = "Plein écran", -- src\editor\menu_view.lua
|
||||
["Fold or unfold all code folds"] = "Replier ou déplier tous les blocs de code", -- src\editor\menu_edit.lua
|
||||
["Found auto-recovery record and restored saved session."] = "Une récupération automatique a été trouvé et la session a été restaurée.", -- src\editor\commands.lua
|
||||
["Full &Screen"] = "&Plein écran", -- src\editor\menu_view.lua
|
||||
["Go to a selected line"] = "Aller à la ligne sélectionnée", -- src\editor\menu_search.lua
|
||||
["Goto Line"] = "Aller à la ligne", -- src\editor\menu_search.lua
|
||||
["INS"] = "INS", -- src\editor\editor.lua
|
||||
["Jump to a function definition..."] = "Aller à la définition de fonction...", -- src\editor\editor.lua
|
||||
["Known Files"] = "Fichiers connus", -- src\editor\commands.lua
|
||||
["Ln: %d"] = "Ln: %d", -- src\editor\editor.lua
|
||||
["Ln: %d"] = "Lig : %d", -- src\editor\editor.lua
|
||||
["Local console"] = "Console locale", -- src\editor\shellbox.lua, src\editor\gui.lua
|
||||
["Lua &Interpreter"] = "Interpréteur Lua", -- src\editor\menu_project.lua
|
||||
["Lua &Interpreter"] = "Interpréteur L&ua", -- src\editor\menu_project.lua
|
||||
["OVR"] = "OVR", -- src\editor\editor.lua
|
||||
["Open an existing document"] = "Ouvrir un document existant", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Open file"] = "Ouvrir un fichier", -- src\editor\commands.lua
|
||||
["Output (running)"] = "Sortie (en cours d'exécution)", -- src\editor\output.lua
|
||||
["Output"] = "Sortie", -- src\editor\output.lua, src\editor\settings.lua, src\editor\gui.lua
|
||||
["Paste text from the clipboard"] = "Coller le texte depuis le presse-papiers", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Prepend '=' to show complex values on multiple lines."] = "Préfixer '=' afin de mettre en évidence les valeurs complexes sur les lignes multiples", -- src\editor\shellbox.lua
|
||||
["Press cancel to abort."] = "Appuyer annuler pour arrêter.", -- src\editor\commands.lua
|
||||
["Program '%s' started in '%s' (pid: %d)."] = "Programme '%s' démarré dans '%s' (pid: %d).", -- src\editor\output.lua
|
||||
["Program can't start because conflicting process is running as '%s'."] = "Le programme ne peut démarrer à cause d'un processus conflictuel '%s' en cours d'exécution.", -- src\editor\output.lua
|
||||
["Program completed in %.2f seconds (pid: %d)."] = "Programme terminé en %.2f secondes (pid: %d).", -- src\editor\output.lua
|
||||
["Prepend '=' to show complex values on multiple lines."] = "Préfixez par '=' pour afficher les valeurs complexes sur plusieurs lignes.", -- src\editor\shellbox.lua
|
||||
["Press cancel to abort."] = "Cliquez sur Annuler pour annuler.", -- src\editor\commands.lua
|
||||
["Program '%s' started in '%s' (pid: %d)."] = "Programme '%s' démarré dans '%s' (pid : %d).", -- src\editor\output.lua
|
||||
["Program can't start because conflicting process is running as '%s'."] = "Le programme ne peut démarrer à cause d'un conflit de processus avec '%s' (en cours d'exécution).", -- src\editor\output.lua
|
||||
["Program completed in %.2f seconds (pid: %d)."] = "Programme terminé en %.2f secondes (pid : %d).", -- src\editor\output.lua
|
||||
["Program starting as '%s'."] = "Programme démarré en tant que '%s'.", -- src\editor\output.lua
|
||||
["Program stopped (pid: %d)."] = "Programme stoppé (pid: %d).", -- src\editor\debugger.lua
|
||||
["Program unable to run as '%s'."] = "Impossible d'écuter le programme en tant que '%s'.", -- src\editor\output.lua
|
||||
["Program stopped (pid: %d)."] = "Programme stoppé (pid : %d).", -- src\editor\debugger.lua
|
||||
["Program unable to run as '%s'."] = "Impossible d'exécuter le programme en tant que '%s'.", -- src\editor\output.lua
|
||||
["Project Directory"] = "Répertoire de projet", -- src\editor\menu_project.lua
|
||||
["Project"] = "Projet", -- src\editor\settings.lua, src\editor\gui.lua
|
||||
["Project/&FileTree Window"] = "Projet/Arborescence de fichiers", -- src\editor\menu_view.lua
|
||||
["Project/&FileTree Window"] = "&Explorateur de projet", -- src\editor\menu_view.lua
|
||||
["R/O"] = "R/O", -- src\editor\editor.lua
|
||||
["R/W"] = "R/W", -- src\editor\editor.lua
|
||||
["Re&place In Files"] = "Remplacer dans les fichiers", -- src\editor\menu_search.lua
|
||||
["Re&place In Files"] = "Remp&lacer dans les fichiers...", -- src\editor\menu_search.lua
|
||||
["Recent Files"] = "Fichiers récents", -- src\editor\menu_file.lua
|
||||
["Redo last edit undone"] = "Refaire la dernière édition annulée", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Refused a request to start a new debugging session as there is one in progress already."] = "Impossible de lancer une nouvelle session de débogage en plus de celle en cours.", -- src\editor\debugger.lua
|
||||
["Redo last edit undone"] = "Rétablir la dernière modification", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Refused a request to start a new debugging session as there is one in progress already."] = "Une requête de lancement de débogage a été refusée car une session de débogage est déjà en cours.", -- src\editor\debugger.lua
|
||||
["Remote console"] = "Console à distance", -- src\editor\shellbox.lua
|
||||
["Reset to default layout"] = "Retourner à l'affiche par défaut", -- src\editor\menu_view.lua
|
||||
["Resets the dynamic word list for autocompletion"] = "Redéfinir la liste des mots dynamiques pour auto-complétion", -- src\editor\menu_edit.lua
|
||||
["Run as Scratchpad"] = "Exécuter en Brouillon", -- src\editor\menu_project.lua
|
||||
["S&top Debugging"] = "Arrêter le débogueur", -- src\editor\menu_project.lua
|
||||
["S&top Process"] = "Arrêter le processus", -- src\editor\menu_project.lua
|
||||
["Save &As..."] = "Enregitrer sous...", -- src\editor\menu_file.lua
|
||||
["Save A&ll"] = "Enregister tout", -- src\editor\menu_file.lua
|
||||
["Save Changes?"] = "Enregister les modifications?", -- src\editor\commands.lua
|
||||
["Save all open documents"] = "Enregister tous les documents ouverts", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Save file as"] = "Enregsitrer le fichier sous", -- src\editor\commands.lua
|
||||
["Save file?"] = "Enregister le fichier?", -- src\editor\commands.lua
|
||||
["Save the current document to a file with a new name"] = "Enregister une copie du document en cours sous", -- src\editor\menu_file.lua
|
||||
["Save the current document"] = "Enregister le document en cours", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Saved auto-recover at %s."] = "Auto-enregistré à %s.", -- src\editor\commands.lua
|
||||
["Scratchpad error"] = "Erreur dans le Brouillon", -- src\editor\debugger.lua
|
||||
["Select &All"] = "Sélectionner tout", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["Reset to default layout"] = "Restaurer l'affichage par défaut", -- src\editor\menu_view.lua
|
||||
["Resets the dynamic word list for autocompletion"] = "Réinitialiser la liste des mots dynamiques pour l'auto-complétion", -- src\editor\menu_edit.lua
|
||||
["Run as Scratchpad"] = "Exécuter comme brouillon", -- src\editor\menu_project.lua
|
||||
["S&top Debugging"] = "&Arrêter le débogage", -- src\editor\menu_project.lua
|
||||
["S&top Process"] = "&Arrêter le processus", -- src\editor\menu_project.lua
|
||||
["Save &As..."] = "Enregistrer &sous...", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Save A&ll"] = "Enregistrer &tout", -- src\editor\menu_file.lua
|
||||
["Save Changes?"] = "Enregistrer les modifications ?", -- src\editor\commands.lua
|
||||
["Save all open documents"] = "Enregistrer tous les documents ouverts", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Save file as"] = "Enregistrer le fichier sous", -- src\editor\commands.lua
|
||||
["Save file?"] = "Enregistrer le fichier ?", -- src\editor\commands.lua
|
||||
["Save the current document to a file with a new name"] = "Enregistrer le document courant sous un nouveau nom", -- src\editor\menu_file.lua
|
||||
["Save the current document"] = "Enregistrer le document courant", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Saved auto-recover at %s."] = "Récup. auto enregistrée à %s.", -- src\editor\commands.lua
|
||||
["Scratchpad error"] = "Erreur dans le brouillon", -- src\editor\debugger.lua
|
||||
["Select &All"] = "Sélectionner &tout", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["Select all text in the editor"] = "Sélectionner tout le texte dans l'éditeur", -- src\editor\menu_edit.lua
|
||||
["Set project directory from current file"] = "Définir le répertoire de projet depuis le fichier courant", -- src\editor\gui.lua
|
||||
["Set From Current File"] = "Définir depuis le fichier courant", -- src\editor\menu_project.lua
|
||||
["Set project directory from current file"] = "Définir le répertoire de projet depuis le fichier courant", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Set the interpreter to be used"] = "Définir l'interpréteur à utiliser", -- src\editor\menu_project.lua
|
||||
["Show &Tooltip"] = "Affichier l'info-bulle", -- src\editor\menu_edit.lua
|
||||
["Show tooltip for current position; place cursor after opening bracket of function"] = "Afficher l'info-bulle pour la position actuelle; placer le curseur après avoir ouvert les parenthèses d'arguments de fontion", -- src\editor\menu_edit.lua
|
||||
["Sort selected lines"] = "trier les fichiers sélectionnés", -- src\editor\menu_search.lua
|
||||
["Set the project directory to be used"] = "Définir le répertoire de projet à utiliser", -- src\editor\menu_project.lua
|
||||
["Show &Tooltip"] = "Afficher l'info-&bulle", -- src\editor\menu_edit.lua
|
||||
["Show tooltip for current position; place cursor after opening bracket of function"] = "Afficher l'info-bulle pour la position actuelle ; placez le curseur après la parenthèse ouvrante de la fonction", -- src\editor\menu_edit.lua
|
||||
["Sort selected lines"] = "Trier les lignes sélectionnées", -- src\editor\menu_search.lua
|
||||
["Stack Window"] = "Fenêtre de pile d'éxécution", -- src\editor\debugger.lua
|
||||
["Start &Debugging"] = "Démarrer le débogage", -- src\editor\menu_project.lua
|
||||
["Start debugging"] = "Démarrer le débogage", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step &Into"] = "Pas dans", -- src\editor\menu_project.lua
|
||||
["Step &Over"] = "Pas sur", -- src\editor\menu_project.lua
|
||||
["Step O&ut"] = "Pas en dehors de", -- src\editor\menu_project.lua
|
||||
["Step into"] = "Pas dans", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step out of the current function"] = "Pas en dehors de la fonction courante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step over"] = "Pas par-dessus la fonction courante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Stop the currently running process"] = "Arrêter le processus en cours", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Switch to or from full screen mode"] = "Passer au/Quitter le mode Plein Ecran", -- src\editor\menu_view.lua
|
||||
["Start &Debugging"] = "Lancer le &débogage", -- src\editor\menu_project.lua
|
||||
["Start debugging"] = "Lancer le débogage", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step &Into"] = "Pas à pas détai&llé", -- src\editor\menu_project.lua
|
||||
["Step &Over"] = "Pas à pas so&mmaire", -- src\editor\menu_project.lua
|
||||
["Step O&ut"] = "Pas à pas so&rtant", -- src\editor\menu_project.lua
|
||||
["Step into"] = "Rentrer dans l'instruction suivante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step out of the current function"] = "Sortir de la fonction courante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Step over"] = "Enjamber l'instruction suivante", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Stop the currently running process"] = "Arrêter le processus en cours d'exécution", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Switch to or from full screen mode"] = "Activer ou désactiver le mode plein écran", -- src\editor\menu_view.lua
|
||||
["The API file must be located in a subdirectory of the API directory."] = "Le fichier d'API doit être placé dans un sous-répertoire du répertoire d'API.", -- src\editor\autocomplete.lua
|
||||
["Toggle Break&point"] = "Basculer en Point d'Interruption", -- src\editor\menu_project.lua
|
||||
["Toggle breakpoint"] = "Basculer en point d'interruption", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Tr&ace"] = "Tracer", -- src\editor\menu_project.lua
|
||||
["Trace execution showing each executed line"] = "Traçage d'exécution du code", -- src\editor\menu_project.lua
|
||||
["Toggle Break&point"] = "Créer/Supprimer un &point d'arrêt", -- src\editor\menu_project.lua
|
||||
["Toggle breakpoint"] = "Créer ou supprimer un point d'arrêt", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Tr&ace"] = "&Tracer", -- src\editor\menu_project.lua
|
||||
["Trace execution showing each executed line"] = "Tracer l'exécution en montrant chaque ligne de code exécutée", -- src\editor\menu_project.lua
|
||||
["Unable to load file '%s'."] = "Impossible de charger le le fichier '%s'.", -- src\editor\commands.lua
|
||||
["Unable to save file '%s': %s"] = "Impossible d'enregistrer le fichier '%s': %s", -- src\editor\commands.lua
|
||||
["Unable to stop program (pid: %d), code %d."] = "Impossible d'arrêter le programme (pid: %d), code %d.", -- src\editor\debugger.lua
|
||||
["Undo last edit"] = "Défaire la dernière édition", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Use 'clear' to clear the shell output and the history."] = "Utiliser 'clear' pour effacer la sortie console et l`historique.", -- src\editor\shellbox.lua
|
||||
["Use Shift-Enter for multiline code."] = "Pressez <Shift-Entrée> pour du code multiligne.", -- src\editor\shellbox.lua
|
||||
["Unable to save file '%s': %s"] = "Impossible d'enregistrer le fichier '%s' : %s", -- src\editor\commands.lua
|
||||
["Unable to stop program (pid: %d), code %d."] = "Impossible d'arrêter le programme (pid : %d), code %d.", -- src\editor\debugger.lua
|
||||
["Undo last edit"] = "Annuler la dernière modification", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Use '%s' to see full description."] = "Utilisez '%s' pour voir la description complète.", -- src\editor\editor.lua
|
||||
["Use 'clear' to clear the shell output and the history."] = "Utilisez 'clear' pour effacer la sortie console et l´historique.", -- src\editor\shellbox.lua
|
||||
["Use Shift-Enter for multiline code."] = "Appuyez sur <Shift-Entrée> pour du code multiligne.", -- src\editor\shellbox.lua
|
||||
["Value"] = "Valeur", -- src\editor\debugger.lua
|
||||
["View the output/console window"] = "Voir la sortie en console", -- src\editor\menu_view.lua
|
||||
["View the project/filetree window"] = "Voir l'arborescence des fichiers de projet", -- src\editor\menu_view.lua
|
||||
["View the stack window"] = "Voir la pile d'éxécution", -- src\editor\menu_view.lua, src\editor\gui.lua
|
||||
["View the watch window"] = "Voir la fenêtre d'observation", -- src\editor\menu_view.lua, src\editor\gui.lua
|
||||
["Watch Window"] = "Fenêtre d'observation", -- src\editor\debugger.lua
|
||||
["Welcome to the interactive Lua interpreter."] = "Bienvenue dans l`interpréteur interactif Lua.", -- src\editor\shellbox.lua
|
||||
["You must save the program first."] = "Enregistrez d'abord le programme", -- src\editor\commands.lua
|
||||
["View the output/console window"] = "Afficher la fenêtre de sortie/console", -- src\editor\menu_view.lua
|
||||
["View the project/filetree window"] = "Afficher la fenêtre d'explorateur de projet", -- src\editor\menu_view.lua
|
||||
["View the stack window"] = "Afficher la fenêtre de pile d'éxécution", -- src\editor\menu_view.lua, src\editor\gui.lua
|
||||
["View the watch window"] = "Afficher la fenêtre d'expressions espionnes", -- src\editor\menu_view.lua, src\editor\gui.lua
|
||||
["Watch Window"] = "Fenêtre d'expressions espionnes", -- src\editor\debugger.lua
|
||||
["Welcome to the interactive Lua interpreter."] = "Bienvenue dans l´interpréteur interactif Lua.", -- src\editor\shellbox.lua
|
||||
["You must save the program first."] = "Vous devez d'abord enregistrer le programme.", -- src\editor\commands.lua
|
||||
["on line %d"] = "à la ligne %d", -- src\editor\debugger.lua, src\editor\commands.lua
|
||||
["traced %d instruction"] = {"%d instruction tracée", "%d instructions tracées"} -- src\editor\debugger.lua
|
||||
}
|
||||
|
||||
@@ -3,7 +3,7 @@ return {
|
||||
["&About"] = "Informazioni", -- src\editor\menu_help.lua
|
||||
["&Add Watch"] = "&Aggiungi Espressione di Controllo", -- src\editor\debugger.lua
|
||||
["&Break"] = "Interrompi", -- src\editor\menu_project.lua
|
||||
["&Close page"] = "&Chiudi pagina", -- src\editor\menu_file.lua
|
||||
["&Close Page"] = "&Chiudi pagina", -- src\editor\menu_file.lua
|
||||
["&Compile"] = "&Compila", -- src\editor\menu_project.lua
|
||||
["&Copy"] = "&Copia", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Default Layout"] = "Visualizzazione di &Default", -- src\editor\menu_view.lua
|
||||
|
||||
@@ -3,7 +3,7 @@ return {
|
||||
["&About"] = "&О программе", -- src\editor\menu_help.lua
|
||||
["&Add Watch"] = "&Добавить выражение", -- src\editor\debugger.lua
|
||||
["&Break"] = "Пр&ервать", -- src\editor\menu_project.lua
|
||||
["&Close page"] = "&Закрыть", -- src\editor\menu_file.lua
|
||||
["&Close Page"] = "&Закрыть", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["&Compile"] = "&Компилировать", -- src\editor\menu_project.lua
|
||||
["&Copy"] = "&Копировать", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["&Default Layout"] = "Вид по &умолчанию", -- src\editor\menu_view.lua
|
||||
@@ -23,7 +23,7 @@ return {
|
||||
["&Remove Watch"] = "&Удалить выражение", -- src\editor\debugger.lua
|
||||
["&Replace"] = "За&менить", -- src\editor\menu_search.lua
|
||||
["&Run"] = "За&пустить", -- src\editor\menu_project.lua
|
||||
["&Save"] = "&Сохранить", -- src\editor\menu_file.lua
|
||||
["&Save"] = "&Сохранить", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["&Search"] = "По&иск", -- src\editor\menu_search.lua
|
||||
["&Sort"] = "&Cортировать", -- src\editor\menu_search.lua
|
||||
["&Stack Window"] = "Окно &стека", -- src\editor\menu_view.lua
|
||||
@@ -50,9 +50,12 @@ return {
|
||||
["Can't run the entry point script ('%s')."] = "Ошибка выполнения стартового скрипта ('%s').", -- src\editor\debugger.lua
|
||||
["Can't start debugging session due to internal error '%s'."] = "Невозможно начать отладочную сессию из-за внутренней ошибки '%s'.", -- src\editor\debugger.lua
|
||||
["Can't start debugging without an opened file or with the current file not being saved ('%s')."] = "Невозможно начать отладку без открытого файла или с несохраненным текущим файлом ('%s').", -- src\editor\debugger.lua
|
||||
["Choose ..."] = "Выбрать ...", -- src\editor\menu_project.lua
|
||||
["Choose a project directory"] = "Выберите каталог проекта", -- src\editor\menu_project.lua
|
||||
["Clear &Dynamic Words"] = "Очистить &динамические слова", -- src\editor\menu_edit.lua
|
||||
["Clear the output window before compiling or debugging"] = "Очистить окно вывода перед компиляцией или отладкой", -- src\editor\menu_project.lua
|
||||
["Close &Other Pages"] = "Закрыть &остальные вкладки", -- src\editor\gui.lua
|
||||
["Close A&ll Pages"] = "Закрыть &все вкладки", -- src\editor\gui.lua
|
||||
["Close the current editor window"] = "Закрыть текущее окно редактирования", -- src\editor\menu_file.lua
|
||||
["Co&ntinue"] = "Пр&одолжить", -- src\editor\menu_project.lua
|
||||
["Col: %d"] = "Стб: %d", -- src\editor\editor.lua
|
||||
@@ -70,13 +73,16 @@ return {
|
||||
["Debugger server started at %s:%d."] = "Сервер отладки запущен на %s:%d.", -- src\editor\debugger.lua
|
||||
["Debugging session completed (%s)."] = "Отладочная сессия завершена (%s).", -- src\editor\debugger.lua
|
||||
["Debugging session started in '%s'."] = "Отладочная сессия запущена в '%s'.", -- src\editor\debugger.lua
|
||||
["Debugging suspended at %s:%s (couldn't activate the file)."] = "Отладка остановлена на %s:%s (невозможно открыть файл).", -- src\editor\debugger.lua
|
||||
["Do you want to reload it?"] = "Перезагрузить его?", -- src\editor\editor.lua
|
||||
["Do you want to save the changes to '%s'?"] = "Сохранить изменения в '%s'?", -- src\editor\commands.lua
|
||||
["E&xit"] = "Вы&ход", -- src\editor\menu_file.lua
|
||||
["Enter Lua code and press Enter to run it."] = "Введите код на Lua и нажмите Enter для выполнения.", -- src\editor\shellbox.lua
|
||||
["Enter line number"] = "Введите номер строки", -- src\editor\menu_search.lua
|
||||
["Error while loading API file: %s"] = "Ошибка загрузки файла определений API: %s", -- src\editor\autocomplete.lua
|
||||
["Error while loading configuration file: %s"] = "Ошибка загрузки файла конфигурации: %s", -- src\editor\style.lua
|
||||
["Error while processing API file: %s"] = "Ошибка обработки файла определений API: %s", -- src\editor\autocomplete.lua
|
||||
["Error while processing configuration file: %s"] = "Ошибка обработки файла конфигурации: %s", -- src\editor\style.lua
|
||||
["Error"] = "Ошибка", -- src\editor\commands.lua
|
||||
["Evaluate &Watches"] = "&Вычислить выражения", -- src\editor\debugger.lua
|
||||
["Evaluate in Console"] = "Выполнить в консоли", -- src\editor\editor.lua
|
||||
@@ -124,6 +130,7 @@ return {
|
||||
["Program starting as '%s'."] = "Программа запускается как '%s'.", -- src\editor\output.lua
|
||||
["Program stopped (pid: %d)."] = "Программа завершена (pid: %d).", -- src\editor\debugger.lua
|
||||
["Program unable to run as '%s'."] = "Программа не может быть запущена как '%s'.", -- src\editor\output.lua
|
||||
["Project Directory"] = "Каталог проекта", -- src\editor\menu_project.lua
|
||||
["Project"] = "Проект", -- src\editor\settings.lua, src\editor\gui.lua
|
||||
["Project/&FileTree Window"] = "Окно &проекта/списка файлов", -- src\editor\menu_view.lua
|
||||
["R/O"] = "R/O", -- src\editor\editor.lua
|
||||
@@ -138,7 +145,7 @@ return {
|
||||
["Run as Scratchpad"] = "Запустить как черновик", -- src\editor\menu_project.lua
|
||||
["S&top Debugging"] = "&Завершить отладку", -- src\editor\menu_project.lua
|
||||
["S&top Process"] = "&Завершить процесс", -- src\editor\menu_project.lua
|
||||
["Save &As..."] = "Сохранить &как...", -- src\editor\menu_file.lua
|
||||
["Save &As..."] = "Сохранить &как...", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
["Save A&ll"] = "Сохранить &все", -- src\editor\menu_file.lua
|
||||
["Save Changes?"] = "Сохранить изменения?", -- src\editor\commands.lua
|
||||
["Save all open documents"] = "Сохранить все открытые документы", -- src\editor\menu_file.lua, src\editor\gui.lua
|
||||
@@ -150,8 +157,10 @@ return {
|
||||
["Scratchpad error"] = "Ошибка в черновике", -- src\editor\debugger.lua
|
||||
["Select &All"] = "Выделить &все", -- src\editor\editor.lua, src\editor\menu_edit.lua
|
||||
["Select all text in the editor"] = "Выделить весь текст в редакторе", -- src\editor\menu_edit.lua
|
||||
["Set project directory from current file"] = "Установить каталог проекта по текущему файлу", -- src\editor\gui.lua
|
||||
["Set From Current File"] = "Установить по текущему файлу", -- src\editor\menu_project.lua
|
||||
["Set project directory from current file"] = "Установить каталог проекта по текущему файлу", -- src\editor\menu_project.lua, src\editor\gui.lua
|
||||
["Set the interpreter to be used"] = "Установить используемый интерпретатор", -- src\editor\menu_project.lua
|
||||
["Set the project directory to be used"] = "Установить используемый каталог проекта", -- src\editor\menu_project.lua
|
||||
["Show &Tooltip"] = "Показать &подсказку", -- src\editor\menu_edit.lua
|
||||
["Show tooltip for current position; place cursor after opening bracket of function"] = "Показать подсказку в текущей позиции; переместите курсор в позицию после открывающей скобки функции", -- src\editor\menu_edit.lua
|
||||
["Sort selected lines"] = "Отсортировать выделенные строки", -- src\editor\menu_search.lua
|
||||
@@ -175,6 +184,7 @@ return {
|
||||
["Unable to save file '%s': %s"] = "Ошибка сохранения файла '%s': %s", -- src\editor\commands.lua
|
||||
["Unable to stop program (pid: %d), code %d."] = "Невозможно завершить программу (pid: %d), код %d.", -- src\editor\debugger.lua
|
||||
["Undo last edit"] = "Отменить последнее действие", -- src\editor\menu_edit.lua, src\editor\gui.lua
|
||||
["Use '%s' to see full description."] = "Используйте '%s' для полного описания.", -- src\editor\editor.lua
|
||||
["Use 'clear' to clear the shell output and the history."] = "Используйте команду 'clear' для очистки содержимого окна и истории.", -- src\editor\shellbox.lua
|
||||
["Use Shift-Enter for multiline code."] = "Используйте Shift-Enter для многострочного кода.", -- src\editor\shellbox.lua
|
||||
["Value"] = "Значение", -- src\editor\debugger.lua
|
||||
|
||||
@@ -96,3 +96,39 @@ stylesoutshell = styles
|
||||
|
||||
-- to disable indicators (underlining) on function calls
|
||||
editor.showfncall = false
|
||||
|
||||
-- to change the color of the indicator used for function calls
|
||||
styles.fncall.fg = {240,0,0}
|
||||
|
||||
-- to change the type of the indicator used for function calls
|
||||
styles.fncall.st = wxstc.wxSTC_INDIC_PLAIN
|
||||
--[[ other possible values are:
|
||||
wxSTC_INDIC_PLAIN Single-line underline
|
||||
wxSTC_INDIC_SQUIGGLE Squiggly underline
|
||||
wxSTC_INDIC_TT Line of small T-shapes
|
||||
wxSTC_INDIC_DIAGONAL Diagonal hatching
|
||||
wxSTC_INDIC_STRIKE Strike-out
|
||||
wxSTC_INDIC_BOX Box
|
||||
wxSTC_INDIC_ROUNDBOX Rounded Box (not suppored in the current version?)
|
||||
--]]
|
||||
|
||||
-- to enable additional spec files (like spec/cpp.lua)
|
||||
load.specs(function(file) return file:find('spec[/\\]cpp%.lua$') end)
|
||||
|
||||
-- to specify a default EOL encoding to be used for new files:
|
||||
-- `wxstc.wxSTC_EOL_CRLF` or `wxstc.wxSTC_EOL_LF`;
|
||||
-- `nil` means OS default: CRLF on Windows and OSX and LF on Linux/Unix.
|
||||
-- CRLF as a default on OSX is a bug and is likely to change in future versions.
|
||||
editor.defaulteol = wxstc.wxSTC_EOL_LF
|
||||
|
||||
-- to turn off checking for mixed end-of-line encodings in loaded files
|
||||
editor.checkeol = false
|
||||
|
||||
-- to force execution to continue immediately after starting debugging;
|
||||
-- set to `false` to disable (the interpreter will stop on the first line or
|
||||
-- when debugging starts); some interpreters may use `true` or `false`
|
||||
-- by default, but can be still reconfigured with this setting.
|
||||
debugger.runonstart = true
|
||||
|
||||
-- to set compact fold that doesn't include empty lines after a block
|
||||
editor.foldcompact = true
|
||||
|
||||
75
cfg/xcode-keys.lua
Normal file
75
cfg/xcode-keys.lua
Normal file
@@ -0,0 +1,75 @@
|
||||
-- Copy the content of this file to user.lua;
|
||||
-- see the [configuration](http://studio.zerobrane.com/doc-configuration.html) page for details.
|
||||
|
||||
local G = ...
|
||||
-- Alt-Shift-Cmd-X (Alt maps to Option, Ctrl maps to Command)
|
||||
-- The mapping is largely based on [Xcode Keyboard Shortcuts](http://developer.apple.com/library/mac/#documentation/IDEs/Conceptual/xcode_help-command_shortcuts/MenuCommands/MenuCommands014.html).
|
||||
local xcode = {
|
||||
-- File menu
|
||||
[G.ID_NEW] = "Ctrl-N",
|
||||
[G.ID_OPEN] = "Ctrl-O",
|
||||
[G.ID_CLOSE] = "Ctrl-W",
|
||||
[G.ID_SAVE] = "Ctrl-S",
|
||||
[G.ID_SAVEAS] = "Shift-Ctrl-S",
|
||||
[G.ID_SAVEALL] = "Alt-Ctrl-S",
|
||||
[G.ID_RECENTFILES] = "",
|
||||
[G.ID_EXIT] = "Ctrl-Q",
|
||||
-- Edit menu
|
||||
[G.ID_CUT] = "Ctrl-X",
|
||||
[G.ID_COPY] = "Ctrl-C",
|
||||
[G.ID_PASTE] = "Ctrl-V",
|
||||
[G.ID_SELECTALL] = "Ctrl-A",
|
||||
[G.ID_UNDO] = "Ctrl-Z",
|
||||
[G.ID_REDO] = "Shift-Ctrl-Z",
|
||||
[G.ID_SHOWTOOLTIP] = "Ctrl-T",
|
||||
[G.ID_AUTOCOMPLETE] = "Ctrl-K",
|
||||
[G.ID_AUTOCOMPLETEENABLE] = "",
|
||||
[G.ID_COMMENT] = "Ctrl-U",
|
||||
[G.ID_FOLD] = "F12",
|
||||
[G.ID_CLEARDYNAMICWORDS] = "",
|
||||
-- Search menu
|
||||
[G.ID_FIND] = "Ctrl-F",
|
||||
[G.ID_FINDNEXT] = "Ctrl-G",
|
||||
[G.ID_FINDPREV] = "Shift-Ctrl-G",
|
||||
[G.ID_REPLACE] = "Alt-Ctrl-F",
|
||||
[G.ID_FINDINFILES] = "Shift-Ctrl-F",
|
||||
[G.ID_REPLACEINFILES] = "Alt-Shift-Ctrl-F",
|
||||
[G.ID_GOTOLINE] = "",
|
||||
[G.ID_SORT] = "",
|
||||
-- View menu
|
||||
[G.ID_VIEWFILETREE] = "Shift-Ctrl-P",
|
||||
[G.ID_VIEWOUTPUT] = "Shift-Ctrl-O",
|
||||
[G.ID_VIEWWATCHWINDOW] = "Shift-Ctrl-W",
|
||||
[G.ID_VIEWCALLSTACK] = "Shift-Ctrl-S",
|
||||
[G.ID_VIEWDEFAULTLAYOUT] = "",
|
||||
[G.ID_VIEWFULLSCREEN] = "Shift-Ctrl-A",
|
||||
-- Project menu
|
||||
[G.ID_RUN] = "Ctrl-R",
|
||||
[G.ID_RUNNOW] = "Shift-Ctrl-R",
|
||||
[G.ID_COMPILE] = "Ctrl-B",
|
||||
[G.ID_ANALYZE] = "Shift-Ctrl-B",
|
||||
[G.ID_STARTDEBUG] = "F5",
|
||||
[G.ID_ATTACHDEBUG] = "",
|
||||
[G.ID_STOPDEBUG] = "Ctrl-.",
|
||||
[G.ID_STEP] = "F7",
|
||||
[G.ID_STEPOVER] = "F6",
|
||||
[G.ID_STEPOUT] = "F8",
|
||||
[G.ID_TRACE] = "",
|
||||
[G.ID_BREAK] = "Ctrl-Y",
|
||||
[G.ID_TOGGLEBREAKPOINT] = "Ctrl-\\",
|
||||
[G.ID_CLEAROUTPUT] = "",
|
||||
[G.ID_INTERPRETER] = "",
|
||||
[G.ID_PROJECTDIR] = "",
|
||||
-- Help menu
|
||||
[G.ID_ABOUT] = "F1",
|
||||
-- Watch window menu items
|
||||
[G.ID_ADDWATCH] = "Ins",
|
||||
[G.ID_EDITWATCH] = "F2",
|
||||
[G.ID_REMOVEWATCH] = "Del",
|
||||
[G.ID_EVALUATEWATCH] = "",
|
||||
-- Editor popup menu items
|
||||
[G.ID_QUICKADDWATCH] = "",
|
||||
[G.ID_QUICKEVAL] = "",
|
||||
}
|
||||
|
||||
for id, key in G.pairs(xcode) do keymap[id] = key end
|
||||
@@ -44,7 +44,8 @@ return {
|
||||
local debug = rundebug and not mac
|
||||
if rundebug then
|
||||
-- start running the application right away
|
||||
DebuggerAttachDefault({runstart=true, startwith = file,
|
||||
DebuggerAttachDefault({startwith = file,
|
||||
runstart = ide.config.debugger.runonstart ~= false,
|
||||
redirect = debug and "c", noshell = mac or nil, noeval = mac or nil})
|
||||
|
||||
-- copy mobdebug.lua to Resources/ folder on Win and to the project folder on OSX
|
||||
@@ -59,7 +60,7 @@ return {
|
||||
end
|
||||
end
|
||||
|
||||
local cmd = ('"%s" %s"%s"'):format(corona, debug and "-debug " or "", file)
|
||||
local cmd = ('"%s" %s"%s"'):format(corona, debug and "-debug " or "", file)
|
||||
-- CommandLineRun(cmd,wdir,tooutput,nohide,stringcallback,uid,endcallback)
|
||||
return CommandLineRun(cmd,self:fworkdir(wfilename),true,false,nil,nil,
|
||||
function() ide.debugger.pid = nil end)
|
||||
@@ -72,4 +73,5 @@ return {
|
||||
end,
|
||||
hasdebugger = true,
|
||||
fattachdebug = function(self) DebuggerAttachDefault() end,
|
||||
scratchextloop = true,
|
||||
}
|
||||
|
||||
@@ -4,6 +4,31 @@ local gideros
|
||||
local win = ide.osname == "Windows"
|
||||
local mac = ide.osname == "Macintosh"
|
||||
|
||||
local function exePath()
|
||||
local mainpath = ide.editorFilename:gsub("[^/\\]+$","")
|
||||
local macExe = mainpath..'bin/lua.app/Contents/MacOS/lua'
|
||||
return ide.config.path.lua or
|
||||
(ide.osname == "Windows" and mainpath..[[bin\lua.exe]]
|
||||
or (ide.osname == "Unix" and [[lua]]) -- using installed lua
|
||||
or (wx.wxFileExists(macExe) and macExe or mainpath..[[bin/lua]]))
|
||||
end
|
||||
|
||||
local function isValidPid(bid, cmd)
|
||||
if not bid or bid == -1 or bid == 0 then
|
||||
DisplayOutputLn(("Program unable to run as '%s'."):format(cmd))
|
||||
return
|
||||
end
|
||||
return bid
|
||||
end
|
||||
|
||||
local function waitToComplete(bid)
|
||||
while wx.wxProcess.Exists(bid) do
|
||||
wx.wxSafeYield()
|
||||
wx.wxWakeUpIdle()
|
||||
wx.wxMilliSleep(100)
|
||||
end
|
||||
end
|
||||
|
||||
return {
|
||||
name = "Gideros",
|
||||
description = "Gideros mobile platform",
|
||||
@@ -26,13 +51,13 @@ return {
|
||||
table.insert(paths, p)
|
||||
end
|
||||
if not gideros then
|
||||
DisplayOutput("Can't find gideros executable in any of the folders in PATH: "
|
||||
..table.concat(paths, ", ").."\n")
|
||||
DisplayOutputLn("Can't find gideros executable in any of the folders in PATH: "
|
||||
..table.concat(paths, ", "))
|
||||
return
|
||||
end
|
||||
end
|
||||
if gideros and not wx.wxFileName(gideros):FileExists() then
|
||||
DisplayOutput("Can't find the specified gideros executable '"..gideros.."'.\n")
|
||||
DisplayOutputLn("Can't find the specified gideros executable '"..gideros.."'.")
|
||||
return
|
||||
end
|
||||
|
||||
@@ -43,7 +68,7 @@ return {
|
||||
local giderospath = giderostools:GetPath(wx.wxPATH_GET_VOLUME)
|
||||
local gdrbridge = GetFullPathIfExists(giderospath, win and 'gdrbridge.exe' or 'gdrbridge')
|
||||
if not gdrbridge then
|
||||
DisplayOutput("Can't find gideros bridge executable in '"..giderospath.."'.\n")
|
||||
DisplayOutputLn("Can't find gideros bridge executable in '"..giderospath.."'.")
|
||||
return
|
||||
end
|
||||
|
||||
@@ -51,24 +76,36 @@ return {
|
||||
local file
|
||||
for _, proj in ipairs(FileSysGet(self:fworkdir(wfilename).."/*.gproj", wx.wxFILE)) do
|
||||
if file then
|
||||
DisplayOutput("Found multiple .gproj files in the project directory; ignored '"..proj.."'\n")
|
||||
DisplayOutputLn("Found multiple .gproj files in the project directory; ignored '"..proj.."'.")
|
||||
end
|
||||
file = proj
|
||||
file = file or proj
|
||||
end
|
||||
if not file then
|
||||
DisplayOutput("Can't find gideros project file in the project directory.\n")
|
||||
DisplayOutputLn("Can't find gideros project file in the project directory.")
|
||||
return
|
||||
end
|
||||
|
||||
if rundebug then DebuggerAttachDefault({redirect = "c"}) end
|
||||
if rundebug then DebuggerAttachDefault(
|
||||
{redirect = "c", runstart = ide.config.debugger.runonstart ~= false}) end
|
||||
|
||||
local cmd = ('"%s"'):format(gideros)
|
||||
-- CommandLineRun(cmd,wdir,tooutput,nohide,stringcallback,uid,endcallback)
|
||||
local pid = CommandLineRun(cmd,self:fworkdir(wfilename),not mac,true,nil,nil,
|
||||
function() ide.debugger.pid = nil end)
|
||||
local pid
|
||||
local remote = ide.config.gideros and ide.config.gideros.remote
|
||||
if remote then
|
||||
local cmd = ('"%s" %s "%s"'):format(gdrbridge, 'setip', remote)
|
||||
DisplayOutputLn(("Configuring remote player at %s."):format(remote))
|
||||
local bid = wx.wxExecute(cmd, wx.wxEXEC_ASYNC)
|
||||
if not isValidPid(bid, cmd) then return end
|
||||
waitToComplete(bid) -- wait for a bit to give Gideros chance to connect
|
||||
else
|
||||
local cmd = ('"%s"'):format(gideros)
|
||||
-- CommandLineRun(cmd,wdir,tooutput,nohide,stringcallback,uid,endcallback)
|
||||
pid = CommandLineRun(cmd,self:fworkdir(wfilename),not mac,true,nil,nil,
|
||||
function() ide.debugger.pid = nil end)
|
||||
if not pid then return end
|
||||
end
|
||||
|
||||
do
|
||||
DisplayOutput("Starting the player and waiting for the bridge to connect at '"..gdrbridge.."'.\n")
|
||||
DisplayOutputLn("Starting the player and waiting for the bridge to connect at '"..gdrbridge.."'.")
|
||||
local cmd = ('"%s" %s'):format(gdrbridge, 'isconnected')
|
||||
local attempts, connected = 12
|
||||
for _ = 1, attempts do
|
||||
@@ -76,10 +113,7 @@ return {
|
||||
proc:Redirect()
|
||||
proc:Connect(wx.wxEVT_END_PROCESS, function(event) proc = nil end)
|
||||
local bid = wx.wxExecute(cmd, wx.wxEXEC_ASYNC + wx.wxEXEC_MAKE_GROUP_LEADER, proc)
|
||||
if not bid or bid == -1 or bid == 0 then
|
||||
DisplayOutput(("Program unable to run as '%s'\n"):format(cmd))
|
||||
return
|
||||
end
|
||||
if not isValidPid(bid, cmd) then return end
|
||||
|
||||
local streamin = proc:GetInputStream()
|
||||
for _ = 1, 20 do
|
||||
@@ -94,21 +128,21 @@ return {
|
||||
if connected then break end
|
||||
if connected == nil and proc then
|
||||
wx.wxProcess.Kill(bid, wx.wxSIGKILL, wx.wxKILL_CHILDREN)
|
||||
wx.wxProcess.Kill(pid, wx.wxSIGKILL, wx.wxKILL_CHILDREN)
|
||||
DisplayOutput("Couldn't connect to the player. Try again or check starting the player and the bridge manually.\n")
|
||||
if not remote then wx.wxProcess.Kill(pid, wx.wxSIGKILL, wx.wxKILL_CHILDREN) end
|
||||
DisplayOutputLn("Couldn't connect to the player. Try again or check starting the player and the bridge manually.")
|
||||
return
|
||||
end
|
||||
end
|
||||
if not connected then
|
||||
wx.wxProcess.Kill(pid, wx.wxSIGKILL, wx.wxKILL_CHILDREN)
|
||||
DisplayOutput("Couldn't connect after "..attempts.." attempts. Try again or check starting the player manually.\n")
|
||||
if not remote then wx.wxProcess.Kill(pid, wx.wxSIGKILL, wx.wxKILL_CHILDREN) end
|
||||
DisplayOutputLn("Couldn't connect after "..attempts.." attempts. Try again or check starting the player manually.")
|
||||
return
|
||||
end
|
||||
|
||||
DisplayOutput("Starting project file '"..file.."'.\n")
|
||||
|
||||
cmd = ('"%s" %s "%s"'):format(gdrbridge, 'play', file)
|
||||
wx.wxExecute(cmd, wx.wxEXEC_ASYNC)
|
||||
local cmd = ('"%s" %s "%s"'):format(gdrbridge, 'play', file)
|
||||
DisplayOutputLn(("Starting project file '%s'."):format(file))
|
||||
local bid = wx.wxExecute(cmd, wx.wxEXEC_ASYNC)
|
||||
if not isValidPid(bid, cmd) then return end
|
||||
end
|
||||
return pid
|
||||
end,
|
||||
|
||||
@@ -51,7 +51,9 @@ return {
|
||||
end
|
||||
end
|
||||
|
||||
if rundebug then DebuggerAttachDefault() end
|
||||
if rundebug then
|
||||
DebuggerAttachDefault({runstart = ide.config.debugger.runonstart == true})
|
||||
end
|
||||
|
||||
local cmd = ('"%s" "%s"'):format(gslshell, wfilename:GetFullPath())
|
||||
-- CommandLineRun(cmd,wdir,tooutput,nohide,stringcallback,uid,endcallback)
|
||||
|
||||
@@ -38,7 +38,9 @@ return {
|
||||
return
|
||||
end
|
||||
|
||||
if rundebug then DebuggerAttachDefault() end
|
||||
if rundebug then
|
||||
DebuggerAttachDefault({runstart = ide.config.debugger.runonstart == true})
|
||||
end
|
||||
|
||||
local cmd = ('"%s" "%s"%s'):format(love2d,
|
||||
self:fworkdir(wfilename), rundebug and ' -debug' or '')
|
||||
|
||||
@@ -18,7 +18,7 @@ return {
|
||||
local filepath = wfilename:GetFullPath()
|
||||
local script
|
||||
if rundebug then
|
||||
DebuggerAttachDefault()
|
||||
DebuggerAttachDefault({runstart = ide.config.debugger.runonstart == true})
|
||||
script = rundebug
|
||||
else
|
||||
-- if running on Windows and can't open the file, this may mean that
|
||||
|
||||
116
interpreters/marmalade.lua
Normal file
116
interpreters/marmalade.lua
Normal file
@@ -0,0 +1,116 @@
|
||||
-- Copyright 2011-12 Paul Kulchenko, ZeroBrane LLC
|
||||
|
||||
local quick
|
||||
local win = ide.osname == "Windows"
|
||||
local mac = ide.osname == "Macintosh"
|
||||
local exe = win and [[win32\s3e_simulator_debug.exe]] or [[loader/osx/s3e_simulator_debug]]
|
||||
local s3e = os.getenv("S3E_DIR")
|
||||
|
||||
return {
|
||||
name = "Marmalade Quick",
|
||||
description = "Marmalade Quick mobile framework",
|
||||
api = {"baselib"},
|
||||
frun = function(self,wfilename,rundebug)
|
||||
quick = quick or ide.config.path.quick or (s3e and GetFullPathIfExists(s3e, exe))
|
||||
if not quick then
|
||||
local sep = win and ';' or ':'
|
||||
local path =
|
||||
win and ([[C:\Marmalade]]..sep..[[D:\Marmalade]]..sep..
|
||||
[[C:\Program Files\Marmalade]]..sep..[[D:\Program Files\Marmalade]]..sep..
|
||||
[[C:\Program Files (x86)\Marmalade]]..sep..[[D:\Program Files (x86)\Marmalade]]..sep)
|
||||
or mac and ([[/Developer/Marmalade]]..sep)
|
||||
or ''
|
||||
-- Marmalade can be installed in a folder with version number or without
|
||||
-- so it may be c:\Marmalade\s3e\... or c:\Marmalade\6.2\s3e\...
|
||||
local candidates, paths = {}, {}
|
||||
for p in path:gmatch("[^"..sep.."]+") do
|
||||
table.insert(paths, p)
|
||||
for _, candidate in ipairs(FileSysGet(p.."/*.*", wx.wxDIR)) do
|
||||
if GetFullPathIfExists(candidate, exe) then table.insert(candidates, candidate) end
|
||||
if GetFullPathIfExists(candidate.."/s3e", exe) then table.insert(candidates, candidate.."/s3e") end
|
||||
end
|
||||
end
|
||||
-- multiple candidates may be present, so sort and use the latest.
|
||||
-- only happens if multiple versions are installed and S3E_DIR is not set.
|
||||
table.sort(candidates)
|
||||
if #candidates > 0 then
|
||||
s3e = candidates[#candidates]
|
||||
quick = GetFullPathIfExists(s3e, exe) -- guaranteed to exist
|
||||
else
|
||||
DisplayOutputLn("Can't find Marmalade installation in any of these folders (and S3E_DIR environmental variable is not set): "
|
||||
..table.concat(paths, ", "))
|
||||
return
|
||||
end
|
||||
end
|
||||
|
||||
local projdir = self:fworkdir(wfilename)
|
||||
local file = GetFullPathIfExists(projdir, 'main.lua')
|
||||
if not file then
|
||||
DisplayOutputLn("Can't find 'main.lua' file in the current project folder.")
|
||||
return
|
||||
end
|
||||
|
||||
-- check for *.mkb file; it can be in the same or in the parent folder
|
||||
local mproj, mfile = MergeFullPath(projdir, "./")
|
||||
for _, file in ipairs(FileSysGet(mproj.."*.mkb", wx.wxFILE)) do mfile = file end
|
||||
if not mfile then
|
||||
mproj, mfile = MergeFullPath(projdir, "../")
|
||||
for _, file in ipairs(FileSysGet(mproj.."*.mkb", wx.wxFILE)) do mfile = file end
|
||||
end
|
||||
if not mfile then
|
||||
DisplayOutputLn(("Can't find '%s' project file."):format(mproj))
|
||||
return
|
||||
end
|
||||
|
||||
local mkb = FileRead(mfile)
|
||||
local datadir = mkb:match("options%s*%{[^%}]*s3e%-data%-dir%s*=%s*(.-)%s*[\r\n%}]")
|
||||
datadir = datadir and datadir:gsub("^['\"]", ""):gsub("['\"][\r\n]*$", "")
|
||||
local icf1, icf2 = mkb:match("options%s*%{[^%}]*app%-icf%s*=%s*(.-)%s*[\r\n%}]")
|
||||
icf1 = icf1 and icf1:gsub("^['\"]", ""):gsub("['\"][\r\n]*$", "")
|
||||
if icf1 and icf1:find(",") then
|
||||
icf1, icf2 = icf1:match("(.+),(.*)")
|
||||
end
|
||||
|
||||
datadir = datadir and (wx.wxIsAbsolutePath(datadir) and datadir or MergeFullPath(mproj, datadir))
|
||||
icf1 = icf1 and (wx.wxIsAbsolutePath(icf1) and icf1 or MergeFullPath(mproj, icf1))
|
||||
icf2 = icf2 and (wx.wxIsAbsolutePath(icf2) and icf2 or MergeFullPath(mproj, icf2))
|
||||
|
||||
if rundebug then
|
||||
-- start running the application right away
|
||||
DebuggerAttachDefault({redirect = mac and "r" or "c", basedir = datadir,
|
||||
runstart = ide.config.debugger.runonstart ~= false})
|
||||
|
||||
-- copy mobdebug.lua to the configured datadir or project folder
|
||||
local mdbc = MergeFullPath(datadir or projdir, "mobdebug.lua")
|
||||
local mdbl = MergeFullPath(GetPathWithSep(ide.editorFilename), "lualibs/mobdebug/mobdebug.lua")
|
||||
if not wx.wxFileExists(mdbc)
|
||||
or GetFileModTime(mdbc):GetTicks() < GetFileModTime(mdbl):GetTicks() then
|
||||
FileCopy(mdbl, mdbc)
|
||||
DisplayOutputLn("Copied ZeroBrane Studio debugger ('mobdebug.lua') to the project folder.")
|
||||
end
|
||||
end
|
||||
|
||||
local dll = MergeFullPath(s3e, "../quick/target/quick_prebuilt_d.s86")
|
||||
local options = table.concat({
|
||||
([[--dll="%s"]]):format(dll),
|
||||
(datadir and ([[--data="%s"]]):format(datadir) or ''),
|
||||
-- Quick doesn't handle correctly spaces in quoted parameters on OSX,
|
||||
-- so replace those with escaped spaces; still quote on Windows
|
||||
(icf1 and ([[--app-icf1=%s]]):format(mac and icf1:gsub(" ", "\\ ") or '"'..icf1..'"') or ''),
|
||||
(icf2 and ([[--app-icf2=%s]]):format(mac and icf2:gsub(" ", "\\ ") or '"'..icf2..'"') or nil),
|
||||
}, " ")
|
||||
|
||||
local cmd = ('"%s" %s'):format(quick, options)
|
||||
-- CommandLineRun(cmd,wdir,tooutput,nohide,stringcallback,uid,endcallback)
|
||||
return CommandLineRun(cmd,GetPathWithSep(projdir),true,true,nil,nil,
|
||||
function() ide.debugger.pid = nil end)
|
||||
end,
|
||||
fprojdir = function(self,wfilename)
|
||||
return wfilename:GetPath(wx.wxPATH_GET_VOLUME)
|
||||
end,
|
||||
fworkdir = function(self,wfilename)
|
||||
return ide.config.path.projectdir or wfilename:GetPath(wx.wxPATH_GET_VOLUME)
|
||||
end,
|
||||
hasdebugger = true,
|
||||
fattachdebug = function(self) DebuggerAttachDefault() end,
|
||||
}
|
||||
@@ -46,7 +46,8 @@ return {
|
||||
|
||||
if rundebug then
|
||||
-- start running the application right away
|
||||
DebuggerAttachDefault({runstart=true, startwith = file})
|
||||
DebuggerAttachDefault({startwith = file,
|
||||
runstart = ide.config.debugger.runonstart ~= false})
|
||||
local code = (
|
||||
[[xpcall(function()
|
||||
io.stdout:setvbuf('no')
|
||||
@@ -63,6 +64,14 @@ return {
|
||||
end
|
||||
f:write(code)
|
||||
f:close()
|
||||
|
||||
-- add mobdebug as the first path to LUA_PATH to provide a workaround
|
||||
-- for a MOAI issue: https://github.com/pkulchenko/ZeroBraneStudio/issues/96
|
||||
local mdb = MergeFullPath(GetPathWithSep(ide.editorFilename), "lualibs/mobdebug/?.lua")
|
||||
local _, path = wx.wxGetEnv("LUA_PATH")
|
||||
if path and path:find(mdb, 1, true) ~= 1 then
|
||||
wx.wxSetEnv("LUA_PATH", mdb..";"..path)
|
||||
end
|
||||
end
|
||||
|
||||
file = file or wfilename:GetFullPath()
|
||||
|
||||
@@ -2,7 +2,7 @@
|
||||
-- an abstract syntax tree (AST)
|
||||
local file = debug.getinfo(1, "S").source
|
||||
if string.find(file, "@") == 1 then file = string.sub(file, 2) end
|
||||
package.path = package.path .. ';' .. string.gsub(file, "metalua%.lua$", "?.lua")
|
||||
package.path = string.gsub(file, "metalua%.lua$", "?.lua") .. ';' .. package.path
|
||||
|
||||
-- these modules are sufficient to build an AST from a source file/string
|
||||
require "lexer"
|
||||
|
||||
@@ -1,12 +1,12 @@
|
||||
--
|
||||
-- MobDebug 0.5084
|
||||
-- MobDebug 0.517
|
||||
-- Copyright 2011-12 Paul Kulchenko
|
||||
-- Based on RemDebug 1.0 Copyright Kepler Project 2005
|
||||
--
|
||||
|
||||
local mobdebug = {
|
||||
_NAME = "mobdebug",
|
||||
_VERSION = 0.5084,
|
||||
_VERSION = 0.517,
|
||||
_COPYRIGHT = "Paul Kulchenko",
|
||||
_DESCRIPTION = "Mobile Remote Debugger for the Lua programming language",
|
||||
port = os and os.getenv and os.getenv("MOBDEBUG_PORT") or 8172,
|
||||
@@ -16,7 +16,8 @@ local mobdebug = {
|
||||
local coroutine = coroutine
|
||||
local error = error
|
||||
local getfenv = getfenv
|
||||
local loadstring = loadstring
|
||||
local setfenv = setfenv
|
||||
local loadstring = loadstring or load -- "load" replaced "loadstring" in Lua 5.2
|
||||
local io = io
|
||||
local os = os
|
||||
local pairs = pairs
|
||||
@@ -34,162 +35,44 @@ local tonumber = tonumber
|
||||
-- the debug loop as 'wx' can be loaded at any time during debugging.
|
||||
local genv = _G or _ENV
|
||||
local jit = rawget(genv, "jit")
|
||||
local mosync = rawget(genv, "mosync")
|
||||
local MOAICoroutine = rawget(genv, "MOAICoroutine")
|
||||
|
||||
if not setfenv then -- Lua 5.2
|
||||
-- based on http://lua-users.org/lists/lua-l/2010-06/msg00314.html
|
||||
-- this assumes f is a function
|
||||
local function findenv(f)
|
||||
local level = 1
|
||||
repeat
|
||||
local name, value = debug.getupvalue(f, level)
|
||||
if name == '_ENV' then return level, value end
|
||||
level = level + 1
|
||||
until name == nil
|
||||
return nil end
|
||||
getfenv = function (f) return(select(2, findenv(f)) or _G) end
|
||||
setfenv = function (f, t)
|
||||
local level = findenv(f)
|
||||
if level then debug.setupvalue(f, level, t) end
|
||||
return f end
|
||||
end
|
||||
|
||||
-- check for OS and convert file names to lower case on windows
|
||||
-- (its file system is case insensitive, but case preserving), as setting a
|
||||
-- breakpoint on x:\Foo.lua will not work if the file was loaded as X:\foo.lua.
|
||||
local iswindows = os.getenv('WINDIR')
|
||||
or (os.getenv('OS') or ''):match('[Ww]indows')
|
||||
local iswindows = os and os.getenv and (os.getenv('WINDIR')
|
||||
or (os.getenv('OS') or ''):match('[Ww]indows'))
|
||||
or pcall(require, "winapi")
|
||||
|
||||
-- this is a socket class that implements maConnect interface
|
||||
local function socketMobileLua()
|
||||
local self = {}
|
||||
self.select = function(readfrom) -- writeto and timeout parameters are ignored
|
||||
local canread = {}
|
||||
for _,s in ipairs(readfrom) do
|
||||
if s:receive(0) then canread[s] = true end
|
||||
end
|
||||
return canread
|
||||
end
|
||||
self.connect = coroutine.wrap(function(host, port)
|
||||
while true do
|
||||
local connection = mosync.maConnect("socket://" .. host .. ":" .. port)
|
||||
|
||||
if connection > 0 then
|
||||
local event = mosync.SysEventCreate()
|
||||
while true do
|
||||
mosync.maWait(0)
|
||||
mosync.maGetEvent(event)
|
||||
local eventType = mosync.SysEventGetType(event)
|
||||
if (mosync.EVENT_TYPE_CONN == eventType and
|
||||
mosync.SysEventGetConnHandle(event) == connection and
|
||||
mosync.SysEventGetConnOpType(event) == mosync.CONNOP_CONNECT) then
|
||||
-- result > 0 ? success : error
|
||||
if not (mosync.SysEventGetConnResult(event) > 0) then connection = nil end
|
||||
break
|
||||
elseif mosync.EventMonitor and mosync.EventMonitor.HandleEvent then
|
||||
mosync.EventMonitor:HandleEvent(event)
|
||||
end
|
||||
end
|
||||
mosync.SysFree(event)
|
||||
end
|
||||
|
||||
host, port = coroutine.yield(connection and (function ()
|
||||
local self = {}
|
||||
local outBuffer = mosync.SysAlloc(1000)
|
||||
local inBuffer = mosync.SysAlloc(1000)
|
||||
local event = mosync.SysEventCreate()
|
||||
local recvBuffer = ""
|
||||
function stringToBuffer(s, buffer)
|
||||
local i = 0
|
||||
for c in s:gmatch(".") do
|
||||
i = i + 1
|
||||
local b = s:byte(i)
|
||||
mosync.SysBufferSetByte(buffer, i - 1, b)
|
||||
end
|
||||
return i
|
||||
end
|
||||
function bufferToString(buffer, len)
|
||||
local s = ""
|
||||
for i = 0, len - 1 do
|
||||
local c = mosync.SysBufferGetByte(buffer, i)
|
||||
s = s .. string.char(c)
|
||||
end
|
||||
return s
|
||||
end
|
||||
self.send = coroutine.wrap(function(self, msg)
|
||||
while true do
|
||||
local numberOfBytes = stringToBuffer(msg, outBuffer)
|
||||
mosync.maConnWrite(connection, outBuffer, numberOfBytes)
|
||||
while true do
|
||||
mosync.maWait(0)
|
||||
mosync.maGetEvent(event)
|
||||
local eventType = mosync.SysEventGetType(event)
|
||||
if (mosync.EVENT_TYPE_CONN == eventType and
|
||||
mosync.SysEventGetConnHandle(event) == connection and
|
||||
mosync.SysEventGetConnOpType(event) == mosync.CONNOP_WRITE) then
|
||||
break
|
||||
elseif mosync.EventMonitor and mosync.EventMonitor.HandleEvent then
|
||||
mosync.EventMonitor:HandleEvent(event)
|
||||
end
|
||||
end
|
||||
self, msg = coroutine.yield()
|
||||
end
|
||||
end)
|
||||
self.receive = coroutine.wrap(function(self, len)
|
||||
while true do
|
||||
local line = recvBuffer
|
||||
while (len and string.len(line) < len) -- either we need len bytes
|
||||
or (not len and not line:find("\n")) -- or one line (if no len specified)
|
||||
or (len == 0) do -- only check for new data (select-like)
|
||||
mosync.maConnRead(connection, inBuffer, 1000)
|
||||
while true do
|
||||
if len ~= 0 then mosync.maWait(0) end
|
||||
mosync.maGetEvent(event)
|
||||
local eventType = mosync.SysEventGetType(event)
|
||||
if (mosync.EVENT_TYPE_CONN == eventType and
|
||||
mosync.SysEventGetConnHandle(event) == connection and
|
||||
mosync.SysEventGetConnOpType(event) == mosync.CONNOP_READ) then
|
||||
local result = mosync.SysEventGetConnResult(event)
|
||||
if result > 0 then line = line .. bufferToString(inBuffer, result) end
|
||||
if len == 0 then self, len = coroutine.yield("") end
|
||||
break -- got the event we wanted; now check if we have all we need
|
||||
elseif len == 0 then
|
||||
self, len = coroutine.yield(nil)
|
||||
elseif mosync.EventMonitor and mosync.EventMonitor.HandleEvent then
|
||||
mosync.EventMonitor:HandleEvent(event)
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
if not len then
|
||||
len = string.find(line, "\n") or string.len(line)
|
||||
end
|
||||
|
||||
recvBuffer = string.sub(line, len+1)
|
||||
line = string.sub(line, 1, len)
|
||||
|
||||
self, len = coroutine.yield(line)
|
||||
end
|
||||
end)
|
||||
self.close = coroutine.wrap(function(self)
|
||||
while true do
|
||||
mosync.SysFree(inBuffer)
|
||||
mosync.SysFree(outBuffer)
|
||||
mosync.SysFree(event)
|
||||
mosync.maConnClose(connection)
|
||||
coroutine.yield(self)
|
||||
end
|
||||
end)
|
||||
return self
|
||||
end)())
|
||||
end
|
||||
end)
|
||||
|
||||
return self
|
||||
end
|
||||
|
||||
-- overwrite RunEventLoop in MobileLua as it conflicts with the event
|
||||
-- loop that needs to run to process debugger events (socket read/write).
|
||||
-- event loop functionality is implemented by calling HandleEvent
|
||||
-- while waiting for debugger events.
|
||||
if mosync and mosync.EventMonitor then
|
||||
mosync.EventMonitor.RunEventLoop = function(self) end
|
||||
end
|
||||
|
||||
-- turn jit off based on Mike Pall's comment in this discussion:
|
||||
-- http://www.freelists.org/post/luajit/Debug-hooks-and-JIT,2
|
||||
-- "You need to turn it off at the start if you plan to receive
|
||||
-- reliable hook calls at any later point in time."
|
||||
if jit and jit.off then jit.off() end
|
||||
|
||||
local socket = mosync and socketMobileLua() or (require "socket")
|
||||
|
||||
local socket = require "socket"
|
||||
local debug = require "debug"
|
||||
local coro_debugger
|
||||
local coro_debugee
|
||||
local coroutines = {}; setmetatable(coroutines, {__mode = "k"}) -- "weak" keys
|
||||
local events = { BREAK = 1, WATCH = 2, RESTART = 3, STACK = 4 }
|
||||
local breakpoints = {}
|
||||
local watches = {}
|
||||
@@ -218,7 +101,7 @@ end
|
||||
local function q(s) return s:gsub('([%(%)%.%%%+%-%*%?%[%^%$%]])','%%%1') end
|
||||
|
||||
local serpent = (function() ---- include Serpent module for serialization
|
||||
local n, v = "serpent", 0.20 -- (C) 2012 Paul Kulchenko; MIT License
|
||||
local n, v = "serpent", 0.22 -- (C) 2012 Paul Kulchenko; MIT License
|
||||
local c, d = "Paul Kulchenko", "Serializer and pretty printer of Lua data types"
|
||||
local snum = {[tostring(1/0)]='1/0 --[[math.huge]]',[tostring(-1/0)]='-1/0 --[[-math.huge]]',[tostring(0/0)]='0/0'}
|
||||
local badtype = {thread = true, userdata = true}
|
||||
@@ -278,7 +161,7 @@ local function s(t, opts)
|
||||
if level >= maxl then return tag..'{}'..comment('max', level) end
|
||||
seen[t] = insref or spath -- set path to use as reference
|
||||
if getmetatable(t) and getmetatable(t).__tostring
|
||||
then return tag..safestr(tostring(t))..comment("meta", level) end
|
||||
then return tag..val2str(tostring(t),nil,indent,false,nil,nil,level+1)..comment("meta", level) end
|
||||
if next(t) == nil then return tag..'{}'..comment(t, level) end -- table empty
|
||||
local maxn, o, out = #t, {}, {}
|
||||
for key = 1, maxn do table.insert(o, key) end
|
||||
@@ -286,7 +169,9 @@ local function s(t, opts)
|
||||
if opts.sortkeys then alphanumsort(o, opts.sortkeys) end
|
||||
for n, key in ipairs(o) do
|
||||
local value, ktype, plainindex = t[key], type(key), n <= maxn and not sparse
|
||||
if opts.ignore and opts.ignore[value] -- skip ignored values; do nothing
|
||||
if opts.valignore and opts.valignore[value] -- skip ignored values; do nothing
|
||||
or opts.keyallow and not opts.keyallow[key]
|
||||
or opts.valtypeignore and opts.valtypeignore[type(value)] -- skipping ignored value types
|
||||
or sparse and value == nil then -- skipping nils; do nothing
|
||||
elseif ktype == 'table' or ktype == 'function' or badtype[ktype] then
|
||||
if not seen[key] and not globals[key] then
|
||||
@@ -319,6 +204,17 @@ return { _NAME = n, _COPYRIGHT = c, _DESCRIPTION = d, _VERSION = v, serialize =
|
||||
block = function(a, opts) return s(a, merge({indent = ' ', sortkeys = true, comment = true}, opts)) end }
|
||||
end)() ---- end of Serpent module
|
||||
|
||||
local function removebasedir(path, basedir)
|
||||
if iswindows then
|
||||
-- check if the lowercased path matches the basedir
|
||||
-- if so, return substring of the original path (to not lowercase it)
|
||||
return path:lower():find('^'..q(basedir:lower()))
|
||||
and path:sub(#basedir+1) or path
|
||||
else
|
||||
return string.gsub(path, '^'..q(basedir), '')
|
||||
end
|
||||
end
|
||||
|
||||
local function stack(start)
|
||||
local function vars(f)
|
||||
local func = debug.getinfo(f, "f").func
|
||||
@@ -345,8 +241,16 @@ local function stack(start)
|
||||
for i = (start or 0), 100 do
|
||||
local source = debug.getinfo(i, "Snl")
|
||||
if not source then break end
|
||||
|
||||
-- remove basedir from source
|
||||
local src = source.source
|
||||
if src:find("@") == 1 then
|
||||
src = src:sub(2):gsub("\\", "/")
|
||||
if src:find("%./") == 1 then src = src:sub(3) end
|
||||
end
|
||||
|
||||
table.insert(stack, {
|
||||
{source.name, source.source, source.linedefined,
|
||||
{source.name, removebasedir(src, basedir), source.linedefined,
|
||||
source.currentline, source.what, source.namewhat, source.short_src},
|
||||
vars(i+1)})
|
||||
if source.what == 'main' then break end
|
||||
@@ -355,13 +259,15 @@ local function stack(start)
|
||||
end
|
||||
|
||||
local function set_breakpoint(file, line)
|
||||
if file == '-' and lastfile then file = lastfile end
|
||||
if file == '-' and lastfile then file = lastfile
|
||||
elseif iswindows then file = string.lower(file) end
|
||||
if not breakpoints[file] then breakpoints[file] = {} end
|
||||
breakpoints[file][line] = true
|
||||
end
|
||||
|
||||
local function remove_breakpoint(file, line)
|
||||
if file == '-' and lastfile then file = lastfile end
|
||||
if file == '-' and lastfile then file = lastfile
|
||||
elseif iswindows then file = string.lower(file) end
|
||||
if breakpoints[file] then breakpoints[file][line] = nil end
|
||||
end
|
||||
|
||||
@@ -437,16 +343,14 @@ local function stack_depth(start_depth)
|
||||
return start_depth
|
||||
end
|
||||
|
||||
local function is_safe(stack_level, conservative)
|
||||
local function is_safe(stack_level)
|
||||
-- the stack grows up: 0 is getinfo, 1 is is_safe, 2 is debug_hook, 3 is user function
|
||||
if stack_level == 3 then return true end
|
||||
local main = debug.getinfo(3, "S").source
|
||||
|
||||
for i = 3, stack_level do
|
||||
-- return if it is not safe to abort
|
||||
local info = debug.getinfo(i, "S")
|
||||
if not info then return true end
|
||||
if conservative and info.source ~= main or info.what == "C" then return false end
|
||||
if info.what == "C" then return false end
|
||||
end
|
||||
return true
|
||||
end
|
||||
@@ -463,8 +367,6 @@ local function in_debugger()
|
||||
end
|
||||
|
||||
local function debug_hook(event, line)
|
||||
if abort and is_safe(stack_level) then error(abort) end
|
||||
|
||||
-- (1) LuaJIT needs special treatment. Because debug_hook is set for
|
||||
-- *all* coroutines, and not just the one being debugged as in regular Lua
|
||||
-- (http://lua-users.org/lists/lua-l/2011-06/msg00513.html),
|
||||
@@ -475,10 +377,20 @@ local function debug_hook(event, line)
|
||||
-- 'tail return' events are not generated by LuaJIT).
|
||||
-- the next line checks if the debugger is run under LuaJIT and if
|
||||
-- one of debugger methods is present in the stack, it simply returns.
|
||||
-- (2) also check if this debug hook has not been visited for any reason.
|
||||
if jit then
|
||||
local coro = coroutine.running()
|
||||
if coro_debugee and coro ~= coro_debugee and not coroutines[coro]
|
||||
or not coro_debugee and (in_debugger() or coro and not coroutines[coro])
|
||||
then return end
|
||||
end
|
||||
|
||||
-- (2) check if abort has been requested and it's safe to abort
|
||||
if abort and is_safe(stack_level) then error(abort) end
|
||||
|
||||
-- (3) also check if this debug hook has not been visited for any reason.
|
||||
-- this check is needed to avoid stepping in too early
|
||||
-- (for example, when coroutine.resume() is executed inside start()).
|
||||
if (jit or not seen_hook) and in_debugger() then return end
|
||||
if not seen_hook and in_debugger() then return end
|
||||
|
||||
if event == "call" then
|
||||
stack_level = stack_level + 1
|
||||
@@ -510,17 +422,24 @@ local function debug_hook(event, line)
|
||||
-- grab the filename and fix it if needed
|
||||
local file = lastfile
|
||||
if (lastsource ~= caller.source) then
|
||||
lastsource = caller.source
|
||||
file = lastsource
|
||||
if string.find(file, "@") == 1 then file = string.sub(file, 2) end
|
||||
file, lastsource = caller.source, caller.source
|
||||
-- the easiest/fastest way would be to check for file names starting
|
||||
-- with '@', but users can supply names that may not use '@',
|
||||
-- for example when they call loadstring('...', 'filename.lua').
|
||||
-- so we handle all sources as filenames
|
||||
file = file:gsub("^@", ""):gsub("\\", "/")
|
||||
-- need this conversion to be applied to relative and absolute
|
||||
-- file names as you may write "require 'Foo'" on Windows to
|
||||
-- load "foo.lua" (as it's case insensitive) and breakpoints
|
||||
-- set on foo.lua will not work if not converted to the same case.
|
||||
if iswindows then file = string.lower(file) end
|
||||
file = string.gsub(file, "\\", "/") -- convert slash
|
||||
-- remove references to the current folder (./)
|
||||
if string.find(file, "%./") == 1 then file = string.sub(file, 3)
|
||||
else file = string.gsub(file, '^'..q(basedir), '') end
|
||||
-- fix filenames for loaded strings that may contain scripts with newlines
|
||||
if string.find(file, "\n") then
|
||||
file = string.sub(string.gsub(file, "\n", ' '), 1, 32) -- limit to 32 chars
|
||||
if file:find("%./") == 1 then file = file:sub(3)
|
||||
else file = file:gsub('^'..q(basedir), '') end
|
||||
|
||||
-- fix filenames for loaded strings that may contain scripts with newlines;
|
||||
-- some filesystems may allow "\n" in filenames, which is not supported here.
|
||||
if file:find("\n") then
|
||||
file = file:gsub("\n", ' '):sub(1, 32) -- limit to 32 chars
|
||||
end
|
||||
|
||||
-- set to true if we got here; this only needs to be done once per
|
||||
@@ -562,7 +481,9 @@ local function debug_hook(event, line)
|
||||
while status and res == 'stack' do
|
||||
-- resume with the stack trace and variables
|
||||
if vars then restore_vars(vars) end -- restore vars so they are reflected in stack values
|
||||
status, res = coroutine.resume(coro_debugger, events.STACK, stack(3), file, line)
|
||||
-- this may fail if __tostring method fails at run-time
|
||||
local ok, snapshot = pcall(stack, 4)
|
||||
status, res = coroutine.resume(coro_debugger, ok and events.STACK or events.BREAK, snapshot, file, line)
|
||||
end
|
||||
end
|
||||
|
||||
@@ -574,6 +495,8 @@ local function debug_hook(event, line)
|
||||
-- only abort if safe; if not, there is another (earlier) check inside
|
||||
-- debug_hook, which will abort execution at the first safe opportunity
|
||||
if is_safe(stack_level) then error(abort) end
|
||||
elseif not status and res then
|
||||
error(res, 2) -- report any other (internal) errors back to the application
|
||||
end
|
||||
|
||||
if vars then restore_vars(vars) end
|
||||
@@ -585,18 +508,19 @@ local function stringify_results(status, ...)
|
||||
|
||||
local t = {...}
|
||||
for i,v in pairs(t) do -- stringify each of the returned values
|
||||
t[i] = serpent.line(v, {nocode = true, comment = 1})
|
||||
local ok, res = pcall(serpent.line, v, {nocode = true, comment = 1})
|
||||
t[i] = ok and res or ("%q"):format(res):gsub("\010","n"):gsub("\026","\\026")
|
||||
end
|
||||
-- stringify table with all returned values
|
||||
-- this is done to allow each returned value to be used (serialized or not)
|
||||
-- intependently and to preserve "original" comments
|
||||
return status, serpent.dump(t, {sparse = false})
|
||||
return pcall(serpent.dump, t, {sparse = false})
|
||||
end
|
||||
|
||||
local function debugger_loop(sfile, sline)
|
||||
local function debugger_loop(sev, svars, sfile, sline)
|
||||
local command
|
||||
local app, osname
|
||||
local eval_env = {}
|
||||
local eval_env = svars or {}
|
||||
local function emptyWatch () return false end
|
||||
local loaded = {}
|
||||
for k in pairs(package.loaded) do loaded[k] = true end
|
||||
@@ -630,7 +554,7 @@ local function debugger_loop(sfile, sline)
|
||||
elseif mobdebug.yield then mobdebug.yield()
|
||||
end
|
||||
elseif not line and err == "closed" then
|
||||
error("Debugger connection unexpectedly closed")
|
||||
error("Debugger connection unexpectedly closed", 0)
|
||||
else
|
||||
break
|
||||
end
|
||||
@@ -696,7 +620,7 @@ local function debugger_loop(sfile, sline)
|
||||
else
|
||||
local chunk = server:receive(size)
|
||||
if chunk then -- LOAD a new script for debugging
|
||||
local func, res = loadstring(chunk, name)
|
||||
local func, res = loadstring(chunk, "@"..name)
|
||||
if func then
|
||||
server:send("200 OK 0\n")
|
||||
debugee = func
|
||||
@@ -791,7 +715,7 @@ local function debugger_loop(sfile, sline)
|
||||
elseif command == "BASEDIR" then
|
||||
local _, _, dir = string.find(line, "^[A-Z]+%s+(.+)%s*$")
|
||||
if dir then
|
||||
basedir = dir
|
||||
basedir = iswindows and string.lower(dir) or dir
|
||||
server:send("200 OK\n")
|
||||
else
|
||||
server:send("400 Bad Request\n")
|
||||
@@ -803,16 +727,20 @@ local function debugger_loop(sfile, sline)
|
||||
-- as it requires yielding back to debug_hook it cannot be executed
|
||||
-- if we have not seen the hook yet as happens after start().
|
||||
-- in this case we simply return an empty result
|
||||
if not seen_hook then
|
||||
server:send("200 OK " .. serpent.dump({}) .. "\n")
|
||||
local vars, ev = {}
|
||||
if seen_hook then
|
||||
ev, vars = coroutine.yield("stack")
|
||||
end
|
||||
if ev and ev ~= events.STACK then
|
||||
server:send("401 Error in Execution " .. #vars .. "\n")
|
||||
server:send(vars)
|
||||
else
|
||||
-- yield back to debug hook to get stack information
|
||||
local ev, vars = coroutine.yield("stack")
|
||||
if ev == events.STACK then
|
||||
server:send("200 OK " ..
|
||||
serpent.dump(vars, {nocode = true, sparse = false}) .. "\n")
|
||||
local ok, res = pcall(serpent.dump, vars, {nocode = true, sparse = false})
|
||||
if ok then
|
||||
server:send("200 OK " .. res .. "\n")
|
||||
else
|
||||
server:send("401 Error in Expression 0\n")
|
||||
server:send("401 Error in Execution " .. #res .. "\n")
|
||||
server:send(res)
|
||||
end
|
||||
end
|
||||
elseif command == "OUTPUT" then
|
||||
@@ -826,7 +754,7 @@ local function debugger_loop(sfile, sline)
|
||||
while true do
|
||||
if mode == 'c' then iobase.print(unpack(tbl)) end
|
||||
for n = 1, #tbl do
|
||||
tbl[n] = serpent.line(tbl[n], {nocode = true, comment = false}) end
|
||||
tbl[n] = select(2, pcall(serpent.line, tbl[n], {nocode = true, comment = false})) end
|
||||
local file = table.concat(tbl, "\t").."\n"
|
||||
server:send("204 Output " .. stream .. " " .. #file .. "\n" .. file)
|
||||
tbl = {coroutine.yield()}
|
||||
@@ -846,7 +774,7 @@ local function debugger_loop(sfile, sline)
|
||||
end
|
||||
|
||||
local function connect(controller_host, controller_port)
|
||||
return socket.connect(controller_host, controller_port)
|
||||
return (socket.connect4 or socket.connect)(controller_host, controller_port)
|
||||
end
|
||||
|
||||
local function isrunning()
|
||||
@@ -861,7 +789,7 @@ local function start(controller_host, controller_port)
|
||||
controller_host = controller_host or "localhost"
|
||||
controller_port = controller_port or mobdebug.port
|
||||
|
||||
server = socket.connect(controller_host, controller_port)
|
||||
server = (socket.connect4 or socket.connect)(controller_host, controller_port)
|
||||
if server then
|
||||
rset = {server} -- store hash to avoid recreating it later
|
||||
-- check if we are called from the debugger as this may happen
|
||||
@@ -887,13 +815,14 @@ local function start(controller_host, controller_port)
|
||||
end
|
||||
coro_debugger = coroutine.create(debugger_loop)
|
||||
debug.sethook(debug_hook, "lcr")
|
||||
return coroutine.resume(coro_debugger, file, info.currentline)
|
||||
local ok, res = coroutine.resume(coro_debugger, events.RESTART, capture_vars(), file, info.currentline)
|
||||
if not ok and res then error(res, 2) end
|
||||
return true
|
||||
else
|
||||
print("Could not connect to " .. controller_host .. ":" .. controller_port)
|
||||
end
|
||||
end
|
||||
|
||||
local coro_debugee
|
||||
local function controller(controller_host, controller_port)
|
||||
-- only one debugging session can be run (as there is only one debug hook)
|
||||
if isrunning() then return end
|
||||
@@ -902,7 +831,7 @@ local function controller(controller_host, controller_port)
|
||||
controller_port = controller_port or mobdebug.port
|
||||
|
||||
local exitonerror = not skip -- exit if not running a scratchpad
|
||||
server = socket.connect(controller_host, controller_port)
|
||||
server = (socket.connect4 or socket.connect)(controller_host, controller_port)
|
||||
if server then
|
||||
rset = {server} -- store hash to avoid recreating it later
|
||||
|
||||
@@ -938,6 +867,13 @@ local function controller(controller_host, controller_port)
|
||||
report(debug.traceback(coro_debugee), tostring(err))
|
||||
if exitonerror then break end
|
||||
-- resume once more to clear the response the debugger wants to send
|
||||
-- need to use capture_vars(2) as three would be the level of
|
||||
-- the caller for controller(), but because of the tail call,
|
||||
-- the caller may not exist;
|
||||
-- This is not entirely safe as the user may see the local
|
||||
-- variable from console, but they will be reset anyway.
|
||||
-- This functionality is used when scratchpad is paused to
|
||||
-- gain access to remote console to modify global variables.
|
||||
local status, err = coroutine.resume(coro_debugger, events.RESTART, capture_vars(2))
|
||||
if not status or status and err == "exit" then break end
|
||||
end
|
||||
@@ -960,9 +896,6 @@ local function loop(controller_host, controller_port)
|
||||
return controller(controller_host, controller_port)
|
||||
end
|
||||
|
||||
local coroutines = {}
|
||||
setmetatable(coroutines, {__mode = "k"}) -- "weak" keys
|
||||
|
||||
local function on()
|
||||
if not (isrunning() and server) then return end
|
||||
|
||||
@@ -983,7 +916,8 @@ local function off()
|
||||
local co = coroutine.running()
|
||||
if co then
|
||||
if coroutines[co] then coroutines[co] = false end
|
||||
debug.sethook(co)
|
||||
-- don't remove coroutine hook under LuaJIT as there is only one (global) hook
|
||||
if not jit then debug.sethook(co) end
|
||||
else
|
||||
debug.sethook()
|
||||
end
|
||||
@@ -1046,12 +980,11 @@ local function handle(params, client, options)
|
||||
elseif command == "setb" then
|
||||
_, _, _, file, line = string.find(params, "^([a-z]+)%s+(.-)%s+(%d+)%s*$")
|
||||
if file and line then
|
||||
if iswindows then file = string.lower(file) end
|
||||
file = string.gsub(file, "\\", "/") -- convert slash
|
||||
file = string.gsub(file, '^'..q(basedir), '') -- remove basedir
|
||||
if not breakpoints[file] then breakpoints[file] = {} end
|
||||
file = removebasedir(file, basedir)
|
||||
client:send("SETB " .. file .. " " .. line .. "\n")
|
||||
if client:receive() == "200 OK" then
|
||||
if not breakpoints[file] then breakpoints[file] = {} end
|
||||
breakpoints[file][line] = true
|
||||
else
|
||||
print("Error: breakpoint not inserted")
|
||||
@@ -1083,13 +1016,11 @@ local function handle(params, client, options)
|
||||
elseif command == "delb" then
|
||||
_, _, _, file, line = string.find(params, "^([a-z]+)%s+(.-)%s+(%d+)%s*$")
|
||||
if file and line then
|
||||
if iswindows then file = string.lower(file) end
|
||||
file = string.gsub(file, "\\", "/") -- convert slash
|
||||
file = string.gsub(file, '^'..q(basedir), '') -- remove basedir
|
||||
if not breakpoints[file] then breakpoints[file] = {} end
|
||||
file = removebasedir(file, basedir)
|
||||
client:send("DELB " .. file .. " " .. line .. "\n")
|
||||
if client:receive() == "200 OK" then
|
||||
breakpoints[file][line] = nil
|
||||
if breakpoints[file] then breakpoints[file][line] = nil end
|
||||
else
|
||||
print("Error: breakpoint not removed")
|
||||
end
|
||||
@@ -1162,14 +1093,14 @@ local function handle(params, client, options)
|
||||
file:close()
|
||||
|
||||
local file = string.gsub(exp, "\\", "/") -- convert slash
|
||||
file = string.gsub(file, '^'..q(basedir), '') -- remove basedir
|
||||
file = removebasedir(file, basedir)
|
||||
client:send("LOAD " .. #lines .. " " .. file .. "\n")
|
||||
client:send(lines)
|
||||
end
|
||||
while true do
|
||||
local params = client:receive()
|
||||
local params, err = client:receive()
|
||||
if not params then
|
||||
return nil, nil, "Debugger error: missing response after EXEC/LOAD"
|
||||
return nil, nil, "Debugger connection " .. (err or "error")
|
||||
end
|
||||
local done = true
|
||||
local _, _, status, len = string.find(params, "^(%d+).-%s+(%d+)%s*$")
|
||||
@@ -1252,18 +1183,14 @@ local function handle(params, client, options)
|
||||
return nil, nil, stack
|
||||
end
|
||||
for _,frame in ipairs(stack) do
|
||||
-- remove basedir from short_src or source
|
||||
local src = string.gsub(frame[1][2], "\\", "/") -- convert slash
|
||||
if string.find(src, "@") == 1 then src = string.sub(src, 2) end
|
||||
if string.find(src, "%./") == 1 then src = string.sub(src, 3) end
|
||||
if iswindows then src = string.lower(src) end
|
||||
frame[1][2] = string.gsub(src, '^'..q(basedir), '') -- remove basedir
|
||||
print(serpent.line(frame[1], {comment = false}))
|
||||
end
|
||||
return stack
|
||||
elseif status == "401" then
|
||||
local res = "Error in stack result"
|
||||
print(res)
|
||||
local _, _, len = string.find(resp, "%s+(%d+)%s*$")
|
||||
len = tonumber(len)
|
||||
local res = len > 0 and client:receive(len) or "Invalid stack information."
|
||||
print("Error in expression: " .. res)
|
||||
return nil, nil, res
|
||||
else
|
||||
print("Unknown error")
|
||||
@@ -1288,12 +1215,14 @@ local function handle(params, client, options)
|
||||
elseif command == "basedir" then
|
||||
local _, _, dir = string.find(params, "^[a-z]+%s+(.+)$")
|
||||
if dir then
|
||||
if iswindows then dir = string.lower(dir) end
|
||||
dir = string.gsub(dir, "\\", "/") -- convert slash
|
||||
if not string.find(dir, "/$") then dir = dir .. "/" end
|
||||
|
||||
local remdir = dir:match("\t(.+)")
|
||||
if remdir then dir = dir:gsub("/?\t.+", "/") end
|
||||
basedir = dir
|
||||
|
||||
client:send("BASEDIR "..dir.."\n")
|
||||
client:send("BASEDIR "..(remdir or dir).."\n")
|
||||
local resp = client:receive()
|
||||
local _, _, status = string.find(resp, "^(%d+)%s+%w+%s*$")
|
||||
if status == "200" then
|
||||
@@ -1403,6 +1332,22 @@ local function moai()
|
||||
end
|
||||
end
|
||||
|
||||
-- this is a function that removes all hooks and closes the socket to
|
||||
-- report back to the controller that the debugging is done.
|
||||
-- the script that called `done` can still continue.
|
||||
local function done()
|
||||
if not (isrunning() and server) then return end
|
||||
|
||||
if not jit then
|
||||
for co, debugged in pairs(coroutines) do
|
||||
if debugged then debug.sethook(co) end
|
||||
end
|
||||
end
|
||||
|
||||
debug.sethook()
|
||||
server:close()
|
||||
end
|
||||
|
||||
-- make public functions available
|
||||
mobdebug.listen = listen
|
||||
mobdebug.loop = loop
|
||||
@@ -1414,6 +1359,7 @@ mobdebug.on = on
|
||||
mobdebug.off = off
|
||||
mobdebug.moai = moai
|
||||
mobdebug.coro = coro
|
||||
mobdebug.done = done
|
||||
mobdebug.line = serpent.line
|
||||
mobdebug.dump = serpent.dump
|
||||
mobdebug.yield = nil -- callback
|
||||
|
||||
78
spec/cpp.lua
Normal file
78
spec/cpp.lua
Normal file
@@ -0,0 +1,78 @@
|
||||
-- author: Paul Kulchenko
|
||||
---------------------------------------------------------
|
||||
|
||||
local funccall = "([A-Za-z_][A-Za-z0-9_]*)%s*"
|
||||
|
||||
return {
|
||||
exts = {"cpp", "c", "hpp", "h"},
|
||||
lexer = wxstc.wxSTC_LEX_CPP,
|
||||
apitype = "cpp",
|
||||
linecomment = "//",
|
||||
stylingbits = 5,
|
||||
|
||||
isfncall = function(str)
|
||||
return string.find(str, funccall .. "%(")
|
||||
end,
|
||||
|
||||
lexerstyleconvert = {
|
||||
text = {wxstc.wxSTC_C_IDENTIFIER,},
|
||||
|
||||
lexerdef = {wxstc.wxSTC_C_DEFAULT,},
|
||||
comment = {wxstc.wxSTC_C_COMMENT,
|
||||
wxstc.wxSTC_C_COMMENTLINE,
|
||||
wxstc.wxSTC_C_COMMENTDOC,},
|
||||
stringtxt = {wxstc.wxSTC_C_STRING,
|
||||
wxstc.wxSTC_C_CHARACTER,
|
||||
wxstc.wxSTC_C_VERBATIM,},
|
||||
stringeol = {wxstc.wxSTC_C_STRINGEOL,},
|
||||
preprocessor= {wxstc.wxSTC_C_PREPROCESSOR,},
|
||||
operator = {wxstc.wxSTC_C_OPERATOR,},
|
||||
number = {wxstc.wxSTC_C_NUMBER,},
|
||||
|
||||
keywords0 = {wxstc.wxSTC_C_WORD,},
|
||||
keywords1 = {wxstc.wxSTC_C_WORD2,},
|
||||
},
|
||||
|
||||
keywords = {
|
||||
[[ alignas alignof and and_eq asm auto bitand bitor break case catch
|
||||
class compl const constexpr const_cast continue
|
||||
decltype default delete do dynamic_cast else enum explicit export
|
||||
extern for friend goto if inline mutable namespace new noexcept not
|
||||
not_eq nullptr operator or or_eq private protected public register
|
||||
reinterpret_cast return sizeof static static_assert static_cast
|
||||
struct switch template this thread_local throw try typedef typeid
|
||||
typename union using virtual volatile while xor xor_eq]],
|
||||
[[ NULL bool char char16_t char32_t double false float int long
|
||||
short signed true unsigned void wchar_t]]
|
||||
},
|
||||
}
|
||||
|
||||
--[==[ C-only keywords
|
||||
[[ auto break case const continue default do else enum extern for goto if
|
||||
register return sizeof static struct switch typedef union volatile while]],
|
||||
[[ NULL char double float int long short signed unsigned void]]
|
||||
--]==]
|
||||
|
||||
--[[
|
||||
// Lexical states for SCLEX_CPP
|
||||
%define wxSTC_C_DEFAULT
|
||||
%define wxSTC_C_COMMENT
|
||||
%define wxSTC_C_COMMENTLINE
|
||||
%define wxSTC_C_COMMENTDOC
|
||||
%define wxSTC_C_NUMBER
|
||||
%define wxSTC_C_WORD
|
||||
%define wxSTC_C_STRING
|
||||
%define wxSTC_C_CHARACTER
|
||||
%define wxSTC_C_UUID
|
||||
%define wxSTC_C_PREPROCESSOR
|
||||
%define wxSTC_C_OPERATOR
|
||||
%define wxSTC_C_IDENTIFIER
|
||||
%define wxSTC_C_STRINGEOL
|
||||
%define wxSTC_C_VERBATIM
|
||||
%define wxSTC_C_REGEX
|
||||
%define wxSTC_C_COMMENTLINEDOC
|
||||
%define wxSTC_C_WORD2
|
||||
%define wxSTC_C_COMMENTDOCKEYWORD
|
||||
%define wxSTC_C_COMMENTDOCKEYWORDERROR
|
||||
%define wxSTC_C_GLOBALCLASS
|
||||
]]
|
||||
@@ -19,27 +19,19 @@ return {
|
||||
end,
|
||||
|
||||
lexerstyleconvert = {
|
||||
text = {wxstc.wxSTC_C_IDENTIFIER,
|
||||
wxstc.wxSTC_C_VERBATIM,
|
||||
wxstc.wxSTC_C_REGEX,
|
||||
wxstc.wxSTC_C_REGEX,
|
||||
wxstc.wxSTC_C_GLOBALCLASS,},
|
||||
text = {wxstc.wxSTC_C_IDENTIFIER,},
|
||||
|
||||
lexerdef = {wxstc.wxSTC_C_DEFAULT,},
|
||||
comment = {wxstc.wxSTC_C_COMMENT,
|
||||
wxstc.wxSTC_C_COMMENTLINE,
|
||||
wxstc.wxSTC_C_COMMENTDOC,
|
||||
wxstc.wxSTC_C_COMMENTLINEDOC,
|
||||
wxstc.wxSTC_C_COMMENTDOCKEYWORD,
|
||||
wxstc.wxSTC_C_COMMENTDOCKEYWORDERROR,},
|
||||
wxstc.wxSTC_C_COMMENTDOC,},
|
||||
stringtxt = {wxstc.wxSTC_C_STRING,
|
||||
wxstc.wxSTC_C_CHARACTER,
|
||||
wxstc.wxSTC_C_UUID,},
|
||||
wxstc.wxSTC_C_VERBATIM,},
|
||||
stringeol = {wxstc.wxSTC_C_STRINGEOL,},
|
||||
preprocessor= {wxstc.wxSTC_C_PREPROCESSOR,},
|
||||
operator = {wxstc.wxSTC_C_OPERATOR,},
|
||||
number = {wxstc.wxSTC_C_NUMBER,
|
||||
wxstc.wxSTC_C_WORD},
|
||||
number = {wxstc.wxSTC_C_NUMBER,},
|
||||
|
||||
keywords0 = {wxstc.wxSTC_C_WORD,},
|
||||
keywords1 = {wxstc.wxSTC_C_WORD2,},
|
||||
|
||||
@@ -33,7 +33,7 @@ return {
|
||||
linecomment = "--",
|
||||
sep = "%.:",
|
||||
isfncall = function(str)
|
||||
return string.find(str, funccall .. "%(")
|
||||
return string.find(str, funccall .. "[%({'\"]")
|
||||
end,
|
||||
isfndef = isfndef,
|
||||
isdecindent = function(str)
|
||||
|
||||
@@ -100,6 +100,11 @@ config = {
|
||||
calltipdelay = nil, -- delay to show calltip (in ms)
|
||||
autoactivate = false, -- auto-activate/open files during debugging
|
||||
smartindent = false, -- use smart indentation if spec allows
|
||||
foldcompact = true, -- use compact fold that includes empty lines
|
||||
checkeol = true, -- check for eol encoding on loaded files and use it
|
||||
-- also report mixed eol encodings
|
||||
defaulteol = nil, -- default line-endings for new files; valid values are
|
||||
-- wxstc.wxSTC_EOL_CRLF, wxstc.wxSTC_EOL_LF and nil (OS default)
|
||||
},
|
||||
|
||||
default = {
|
||||
@@ -111,6 +116,8 @@ config = {
|
||||
verbose = false,
|
||||
hostname = nil, -- hostname to use when the detected one is incorrect
|
||||
port = nil, -- port number to use
|
||||
runonstart = nil, -- if debugger should run immediately after starting
|
||||
-- default values are different for different interpreters
|
||||
}
|
||||
|
||||
outputshell = { -- output and shell settings
|
||||
@@ -231,7 +238,7 @@ spec = {
|
||||
linecomment = "//",
|
||||
-- string for linecomments
|
||||
|
||||
sep = "[%.:]",
|
||||
sep = "%.:",
|
||||
-- class.function separator match string,
|
||||
-- e.g in lua both . and : are allowed
|
||||
-- default is "\1" which should yield no matches
|
||||
|
||||
@@ -67,6 +67,27 @@ function LoadFile(filePath, editor, file_must_exist, skipselection)
|
||||
editor:MarkerDeleteAll(BREAKPOINT_MARKER)
|
||||
editor:MarkerDeleteAll(CURRENT_LINE_MARKER)
|
||||
editor:AppendText(file_text or "")
|
||||
|
||||
-- check the editor as it can be empty if the file has malformed UTF8;
|
||||
-- skip binary files as they may have any sequences; can't show them anyway.
|
||||
if file_text and #file_text > 0 and not isBinary(file_text)
|
||||
and #(editor:GetText()) == 0 then
|
||||
local replacement, invalid = "\022"
|
||||
file_text, invalid = fixUTF8(file_text, replacement)
|
||||
if #invalid > 0 then
|
||||
editor:AppendText(file_text)
|
||||
local lastline = nil
|
||||
for _, n in ipairs(invalid) do
|
||||
local line = editor:LineFromPosition(n)
|
||||
if line ~= lastline then
|
||||
DisplayOutputLn(("%s:%d: %s")
|
||||
:format(filePath, line+1, TR("Replaced an invalid UTF8 character with %s."):format(replacement)))
|
||||
lastline = line
|
||||
end
|
||||
end
|
||||
end
|
||||
end
|
||||
|
||||
editor:Colourise(0, -1)
|
||||
editor:Thaw()
|
||||
|
||||
@@ -75,6 +96,24 @@ function LoadFile(filePath, editor, file_must_exist, skipselection)
|
||||
local found = string.find(file_text,"\t") ~= nil
|
||||
editor:SetUseTabs(found)
|
||||
end
|
||||
|
||||
if (ide.config.editor.checkeol) then
|
||||
-- Auto-detect CRLF/LF line-endings
|
||||
local foundcrlf = string.find(file_text,"\r\n") ~= nil
|
||||
local foundlf = (string.find(file_text,"[^\r]\n") ~= nil)
|
||||
or (string.find(file_text,"^\n") ~= nil) -- edge case: file beginning with LF and having no other LF
|
||||
if foundcrlf and foundlf then -- file with mixed line-endings
|
||||
DisplayOutputLn(("%s: %s")
|
||||
:format(filePath, TR("Mixed end-of-line encodings detected.")..' '..
|
||||
TR("Use '%s' to show line endings and '%s' to convert them.")
|
||||
:format("GetEditor():SetViewEOL(1)", "GetEditor():ConvertEOLs(GetEditor():GetEOLMode())")))
|
||||
elseif foundcrlf then
|
||||
editor:SetEOLMode(wxstc.wxSTC_EOL_CRLF)
|
||||
elseif foundlf then
|
||||
editor:SetEOLMode(wxstc.wxSTC_EOL_LF)
|
||||
-- else (e.g. file is 1 line long or uses another line-ending): use default EOL mode
|
||||
end
|
||||
end
|
||||
|
||||
editor:EmptyUndoBuffer()
|
||||
local id = editor:GetId()
|
||||
@@ -285,6 +324,21 @@ function ClosePage(selection)
|
||||
end
|
||||
end
|
||||
|
||||
function CloseAllPagesExcept(selection)
|
||||
local toclose = {}
|
||||
for _, document in pairs(ide.openDocuments) do
|
||||
table.insert(toclose, document.index)
|
||||
end
|
||||
|
||||
table.sort(toclose)
|
||||
|
||||
-- close pages for those files that match the project in the reverse order
|
||||
-- (as ids shift when pages are closed)
|
||||
for i = #toclose, 1, -1 do
|
||||
if toclose[i] ~= selection then ClosePage(toclose[i]) end
|
||||
end
|
||||
end
|
||||
|
||||
-- Show a dialog to save a file before closing editor.
|
||||
-- returns wxID_YES, wxID_NO, or wxID_CANCEL if allow_cancel
|
||||
function SaveModifiedDialog(editor, allow_cancel)
|
||||
|
||||
@@ -32,6 +32,8 @@ local CURRENT_LINE_MARKER_VALUE = 2^CURRENT_LINE_MARKER
|
||||
local BREAKPOINT_MARKER = StylesGetMarker("breakpoint")
|
||||
local BREAKPOINT_MARKER_VALUE = 2^BREAKPOINT_MARKER
|
||||
|
||||
local function q(s) return s:gsub('([%(%)%.%%%+%-%*%?%[%^%$%]])','%%%1') end
|
||||
|
||||
local function updateWatchesSync(num)
|
||||
local watchCtrl = debugger.watchCtrl
|
||||
if watchCtrl and debugger.server and not debugger.running
|
||||
@@ -109,7 +111,9 @@ local function updateStackSync()
|
||||
or " (defined in "..call[2]..")"))
|
||||
local callitem = stackCtrl:AppendItem(root, text, 0)
|
||||
for name,val in pairs(frame[2]) do
|
||||
local value, comment = val[1], val[2]
|
||||
-- comment can be not necessarily a string for tables with metatables
|
||||
-- that provide its own __tostring method
|
||||
local value, comment = val[1], tostring(val[2])
|
||||
local text = ("%s = %s%s"):
|
||||
format(name, mobdebug.line(value, params),
|
||||
simpleType[type(value)] and "" or (" --[["..comment.."]]"))
|
||||
@@ -170,7 +174,7 @@ local function killClient()
|
||||
end
|
||||
end
|
||||
|
||||
local function activateDocument(file, line)
|
||||
local function activateDocument(file, line, skipauto)
|
||||
if not file then return end
|
||||
|
||||
if not wx.wxIsAbsolutePath(file) and debugger.basedir then
|
||||
@@ -185,6 +189,7 @@ local function activateDocument(file, line)
|
||||
if document.filePath and fileName:SameAs(wx.wxFileName(document.filePath)) then
|
||||
local editor = document.editor
|
||||
local selection = document.index
|
||||
RequestAttention()
|
||||
notebook:SetSelection(selection)
|
||||
SetEditorSelection(selection)
|
||||
ClearAllCurrentLineMarkers()
|
||||
@@ -197,7 +202,7 @@ local function activateDocument(file, line)
|
||||
end
|
||||
end
|
||||
|
||||
if not activated and not indebugger and not debugger.loop
|
||||
if not (activated or indebugger or debugger.loop or skipauto)
|
||||
and ide.config.editor.autoactivate then
|
||||
-- found file, but can't activate yet (because this part may be executed
|
||||
-- in a different co-routine), so schedule pending activation.
|
||||
@@ -254,7 +259,7 @@ debugger.shell = function(expression, isstatement)
|
||||
expression = expression:gsub("^%s*=%s*","")
|
||||
local _, values, err = debugger.evaluate(expression)
|
||||
if not forceexpression and err and
|
||||
(err:find("'<eof>' expected near '") or
|
||||
(err:find("'?<eof>'? expected near '") or
|
||||
err:find("'%(' expected near") or
|
||||
err:find("unexpected symbol near '")) then
|
||||
_, values, err = debugger.execute(expression)
|
||||
@@ -380,12 +385,19 @@ debugger.listen = function()
|
||||
-- OR (2) it can "refuse" to load it if the client was started
|
||||
-- with start() method, which can't load new files
|
||||
-- if file and line are set, this indicates option #2
|
||||
if file and line then
|
||||
local activated = activateDocument(file, line)
|
||||
if err then
|
||||
DisplayOutputLn(TR("Can't debug the script in the active editor window.")
|
||||
.." "..TR("Compilation error")
|
||||
..":\n"..err)
|
||||
return debugger.terminate()
|
||||
elseif options.runstart then
|
||||
-- do nothing as no activation is required; the script will be run
|
||||
elseif file and line then
|
||||
local activated = activateDocument(file, line, true)
|
||||
|
||||
-- if not found, check using full file path and reset basedir
|
||||
if not activated and not wx.wxIsAbsolutePath(file) then
|
||||
activated = activateDocument(startpath..file, line)
|
||||
activated = activateDocument(startpath..file, line, true)
|
||||
if activated then
|
||||
debugger.basedir = startpath
|
||||
debugger.handle("basedir " .. debugger.basedir)
|
||||
@@ -394,6 +406,42 @@ debugger.listen = function()
|
||||
end
|
||||
end
|
||||
|
||||
-- if not found and the files doesn't exist, it may be
|
||||
-- a remote call; try to map it to the project folder
|
||||
if not activated and not wx.wxFileName(file):FileExists() then
|
||||
-- file is /foo/bar/my.lua; basedir is d:\local\path\
|
||||
-- check for d:\local\path\my.lua, d:\local\path\bar\my.lua, ...
|
||||
-- wxwidgets on Windows handles \\ and / as separators, but on OSX
|
||||
-- and Linux it only handles 'native' separator;
|
||||
-- need to translate for GetDirs to work.
|
||||
local file = file:gsub("\\", "/")
|
||||
local parts = wx.wxFileName(file):GetDirs()
|
||||
local name = wx.wxFileName(file):GetFullName()
|
||||
|
||||
-- find the longest remote path that can be mapped locally
|
||||
local longestpath, remotedir
|
||||
while true do
|
||||
local mapped = GetFullPathIfExists(basedir, name)
|
||||
if mapped then
|
||||
longestpath = mapped
|
||||
remotedir = file:gsub(q(name):gsub("/", ".").."$", "")
|
||||
end
|
||||
if #parts == 0 then break end
|
||||
name = table.remove(parts, #parts) .. "/" .. name
|
||||
end
|
||||
|
||||
-- if found a local mapping under basedir
|
||||
activated = longestpath and activateDocument(longestpath, line, true)
|
||||
if activated then
|
||||
-- find remote basedir by removing the tail from remote file
|
||||
debugger.handle("basedir " .. debugger.basedir .. "\t" .. remotedir)
|
||||
-- reset breakpoints again as remote basedir has changed
|
||||
reSetBreakpoints()
|
||||
DisplayOutputLn(TR("Mapped remote request for '%s' to '%s'.")
|
||||
:format(remotedir, debugger.basedir))
|
||||
end
|
||||
end
|
||||
|
||||
if not activated then
|
||||
DisplayOutputLn(TR("Can't find file '%s' in the current project to activate for debugging. Update the project or open the file in the editor before debugging.")
|
||||
:format(file))
|
||||
@@ -403,11 +451,6 @@ debugger.listen = function()
|
||||
-- debugger may still be available for scratchpad,
|
||||
-- if the interpreter signals scratchpad support, so enable it.
|
||||
debugger.scratchable = ide.interpreter.scratchextloop ~= nil
|
||||
elseif err then
|
||||
DisplayOutputLn(TR("Can't debug the script in the active editor window.")
|
||||
.." "..TR("Compilation error")
|
||||
..":\n"..err)
|
||||
return debugger.terminate()
|
||||
else
|
||||
debugger.scratchable = true
|
||||
activateDocument(startfile, 1)
|
||||
@@ -613,6 +656,9 @@ end
|
||||
function DebuggerShutdown()
|
||||
if debugger.server then debugger.terminate() end
|
||||
if debugger.pid then killClient() end
|
||||
-- wait for a little bit as in some rare cases when closing the debugger
|
||||
-- with a running application under OSX, the process crashes (wxlua2.8.12).
|
||||
if ide.osname == "Macintosh" then wx.wxMilliSleep(100) end
|
||||
end
|
||||
|
||||
function DebuggerStop()
|
||||
@@ -881,7 +927,6 @@ end
|
||||
|
||||
-- scratchpad functions
|
||||
|
||||
local function q(s) return s:gsub('([%(%)%.%%%+%-%*%?%[%^%$%]])','%%%1') end
|
||||
function DebuggerRefreshScratchpad()
|
||||
if debugger.scratchpad and debugger.scratchpad.updated and not debugger.scratchpad.paused then
|
||||
|
||||
|
||||
@@ -300,6 +300,16 @@ function EditorCallTip(editor, pos, x, y)
|
||||
end
|
||||
end
|
||||
|
||||
function EditorIsModified(editor)
|
||||
local modified = false
|
||||
if editor then
|
||||
local id = editor:GetId()
|
||||
modified = openDocuments[id]
|
||||
and (openDocuments[id].isModified or not openDocuments[id].filePath)
|
||||
end
|
||||
return modified
|
||||
end
|
||||
|
||||
-- ----------------------------------------------------------------------------
|
||||
-- Create an editor
|
||||
function CreateEditor()
|
||||
@@ -330,6 +340,12 @@ function CreateEditor()
|
||||
editor:SetWrapVisualFlagsLocation(wxstc.wxSTC_WRAPVISUALFLAGLOC_END_BY_TEXT)
|
||||
end
|
||||
|
||||
if (ide.config.editor.defaulteol == wxstc.wxSTC_EOL_CRLF
|
||||
or ide.config.editor.defaulteol == wxstc.wxSTC_EOL_LF) then
|
||||
editor:SetEOLMode(ide.config.editor.defaulteol)
|
||||
-- else: keep wxStyledTextCtrl default behavior (CRLF on Windows, LF on Unix)
|
||||
end
|
||||
|
||||
editor:SetCaretLineVisible(ide.config.editor.caretline and 1 or 0)
|
||||
|
||||
editor:SetVisiblePolicy(wxstc.wxSTC_VISIBLE_SLOP, 3)
|
||||
@@ -352,7 +368,7 @@ function CreateEditor()
|
||||
wxstc.wxSTC_FOLDFLAG_LINEAFTER_CONTRACTED)
|
||||
|
||||
editor:SetProperty("fold", "1")
|
||||
editor:SetProperty("fold.compact", "1")
|
||||
editor:SetProperty("fold.compact", ide.config.editor.foldcompact and "1" or "0")
|
||||
editor:SetProperty("fold.comment", "1")
|
||||
|
||||
do
|
||||
@@ -437,7 +453,7 @@ function CreateEditor()
|
||||
local localpos = pos-linestart
|
||||
local linetxtopos = linetx:sub(1,localpos)
|
||||
|
||||
if (ch == char_CR and eol==2) or (ch == char_LF and eol==0) then
|
||||
if (ch == char_LF) then
|
||||
if (line > 0) then
|
||||
local indent = editor:GetLineIndentation(line - 1)
|
||||
local linedone = editor:GetLine(line - 1)
|
||||
@@ -640,13 +656,13 @@ function CreateEditor()
|
||||
editor:Connect(wx.wxEVT_CONTEXT_MENU,
|
||||
function (event)
|
||||
local menu = wx.wxMenu()
|
||||
menu:Append(wx.wxID_UNDO, TR("&Undo"))
|
||||
menu:Append(wx.wxID_REDO, TR("&Redo"))
|
||||
menu:Append(ID_UNDO, TR("&Undo"))
|
||||
menu:Append(ID_REDO, TR("&Redo"))
|
||||
menu:AppendSeparator()
|
||||
menu:Append(wx.wxID_CUT, TR("Cu&t"))
|
||||
menu:Append(wx.wxID_COPY, TR("&Copy"))
|
||||
menu:Append(wx.wxID_PASTE, TR("&Paste"))
|
||||
menu:Append(wx.wxID_SELECTALL, TR("Select &All"))
|
||||
menu:Append(ID_CUT, TR("Cu&t"))
|
||||
menu:Append(ID_COPY, TR("&Copy"))
|
||||
menu:Append(ID_PASTE, TR("&Paste"))
|
||||
menu:Append(ID_SELECTALL, TR("Select &All"))
|
||||
menu:AppendSeparator()
|
||||
menu:Append(ID_QUICKADDWATCH, TR("Add Watch Expression"))
|
||||
menu:Append(ID_QUICKEVAL, TR("Evaluate in Console"))
|
||||
|
||||
@@ -55,7 +55,7 @@ local function treeAddDir(tree,parent_id,rootdir)
|
||||
|
||||
-- append directories
|
||||
for _,dir in ipairs(FileSysGet(search,wx.wxDIR)) do
|
||||
local name = dir:match("%"..string_Pathsep.."("..stringset_File.."+)$")
|
||||
local name = dir:match("("..stringset_File.."+)$")
|
||||
local icon = 0
|
||||
local item = items[name .. icon]
|
||||
if item then -- existing item
|
||||
@@ -79,7 +79,7 @@ local function treeAddDir(tree,parent_id,rootdir)
|
||||
|
||||
-- then append files
|
||||
for _,file in ipairs(FileSysGet(search,wx.wxFILE)) do
|
||||
local name = file:match("%"..string_Pathsep.."("..stringset_File.."+)$")
|
||||
local name = file:match("("..stringset_File.."+)$")
|
||||
local known = GetSpec(GetFileExt(name))
|
||||
local icon = known and 1 or 2
|
||||
local item = items[name .. icon]
|
||||
|
||||
@@ -66,11 +66,13 @@ end
|
||||
local function createToolBar(frame)
|
||||
local toolBar = wx.wxToolBar(frame, wx.wxID_ANY,
|
||||
wx.wxDefaultPosition, wx.wxDefaultSize, wx.wxTB_FLAT + wx.wxTB_NODIVIDER)
|
||||
local funclist = wx.wxChoice.new(toolBar,ID "toolBar.funclist",
|
||||
local funclist = wx.wxChoice.new(toolBar, ID "toolBar.funclist",
|
||||
-- Linux requires a bit larger size for the function list in the toolbar.
|
||||
-- Mac also requires a bit larger size, but setting it to 20 resets
|
||||
-- back to 16 when the toolbar is refreshed.
|
||||
wx.wxDefaultPosition, wx.wxSize.new(240,ide.osname == "Unix" and 24 or 16))
|
||||
-- Windows with wxwidgets 2.9.x also requires a larger size.
|
||||
wx.wxDefaultPosition, wx.wxSize.new(240,
|
||||
(ide.osname == "Unix" or ide.osname == "Windows") and 24 or 16))
|
||||
|
||||
-- usually the bmp size isn't necessary, but the HELP icon is not the right size in MSW
|
||||
local getBitmap = (ide.app.createbitmap or wx.wxArtProvider.GetBitmap)
|
||||
@@ -141,6 +143,47 @@ local function createNotebook(frame)
|
||||
event:Veto() -- don't propagate the event as the page is already closed
|
||||
end)
|
||||
|
||||
local selection
|
||||
notebook:Connect(wxaui.wxEVT_COMMAND_AUINOTEBOOK_TAB_RIGHT_UP,
|
||||
function (event)
|
||||
selection = event:GetSelection() -- save tab index the event is for
|
||||
local menu = wx.wxMenu()
|
||||
menu:Append(ID_CLOSE, TR("&Close Page"))
|
||||
menu:Append(ID_CLOSEALL, TR("Close A&ll Pages"))
|
||||
menu:Append(ID_CLOSEOTHER, TR("Close &Other Pages"))
|
||||
menu:AppendSeparator()
|
||||
menu:Append(ID_SAVE, TR("&Save"))
|
||||
menu:Append(ID_SAVEAS, TR("Save &As..."))
|
||||
notebook:PopupMenu(menu)
|
||||
end)
|
||||
|
||||
local function IfAtLeastOneTab(event) event:Enable(notebook:GetPageCount() > 0) end
|
||||
local function IfModified(event) event:Enable(EditorIsModified(GetEditor(selection))) end
|
||||
|
||||
notebook:Connect(ID_SAVE, wx.wxEVT_COMMAND_MENU_SELECTED, function ()
|
||||
local editor = GetEditor(selection)
|
||||
SaveFile(editor, openDocuments[editor:GetId()].filePath)
|
||||
end)
|
||||
notebook:Connect(ID_SAVE, wx.wxEVT_UPDATE_UI, IfModified)
|
||||
notebook:Connect(ID_SAVEAS, wx.wxEVT_COMMAND_MENU_SELECTED, function()
|
||||
SaveFileAs(GetEditor(selection))
|
||||
end)
|
||||
notebook:Connect(ID_SAVEAS, wx.wxEVT_UPDATE_UI, IfAtLeastOneTab)
|
||||
notebook:Connect(ID_CLOSE, wx.wxEVT_COMMAND_MENU_SELECTED, function()
|
||||
ClosePage(selection)
|
||||
end)
|
||||
notebook:Connect(ID_CLOSE, wx.wxEVT_UPDATE_UI, IfAtLeastOneTab)
|
||||
notebook:Connect(ID_CLOSEALL, wx.wxEVT_COMMAND_MENU_SELECTED, function()
|
||||
CloseAllPagesExcept(nil)
|
||||
end)
|
||||
notebook:Connect(ID_CLOSEALL, wx.wxEVT_UPDATE_UI, IfAtLeastOneTab)
|
||||
notebook:Connect(ID_CLOSEOTHER, wx.wxEVT_COMMAND_MENU_SELECTED, function ()
|
||||
CloseAllPagesExcept(selection)
|
||||
end)
|
||||
notebook:Connect(ID_CLOSEOTHER, wx.wxEVT_UPDATE_UI, function (event)
|
||||
event:Enable(notebook:GetPageCount() > 1)
|
||||
end)
|
||||
|
||||
frame.notebook = notebook
|
||||
return notebook
|
||||
end
|
||||
|
||||
@@ -13,6 +13,8 @@ end
|
||||
ID_NEW = wx.wxID_NEW
|
||||
ID_OPEN = wx.wxID_OPEN
|
||||
ID_CLOSE = NewID()
|
||||
ID_CLOSEALL = NewID()
|
||||
ID_CLOSEOTHER = NewID()
|
||||
ID_SAVE = wx.wxID_SAVE
|
||||
ID_SAVEAS = wx.wxID_SAVEAS
|
||||
ID_SAVEALL = NewID()
|
||||
|
||||
@@ -1,11 +1,27 @@
|
||||
local ide = ide
|
||||
|
||||
function KSC(id, default)
|
||||
-- this is only for the rare case of someone assigning a complete list
|
||||
-- to ide.config.keymap.
|
||||
local keymap = ide.config.keymap
|
||||
return keymap[id] and "\t"..keymap[id] or default or ""
|
||||
end
|
||||
--[[
|
||||
Accelerator general syntax is any combination of "CTRL", "ALT" and "SHIFT"
|
||||
strings (case doesn't matter) separated by either '-' or '+' characters and
|
||||
followed by the accelerator itself. The accelerator may be any alphanumeric
|
||||
character, any function key (from F1 to F12) or one of the special characters
|
||||
listed below (again, case doesn't matter):
|
||||
|
||||
DEL/DELETE Delete key
|
||||
INS/INSERT Insert key
|
||||
ENTER/RETURN Enter key
|
||||
PGUP PageUp key
|
||||
PGDN PageDown key
|
||||
LEFT Left cursor arrow key
|
||||
RIGHT Right cursor arrow key
|
||||
UP Up cursor arrow key
|
||||
DOWN Down cursor arrow key
|
||||
HOME Home key
|
||||
END End key
|
||||
SPACE Space
|
||||
TAB Tab key
|
||||
ESC/ESCAPE Escape key (Windows only)
|
||||
--]]
|
||||
|
||||
ide.config.keymap = {
|
||||
-- File menu
|
||||
@@ -75,25 +91,9 @@ ide.config.keymap = {
|
||||
[ID_QUICKEVAL] = "",
|
||||
}
|
||||
|
||||
--[[
|
||||
Accelerator general syntax is any combination of "CTRL", "ALT" and "SHIFT"
|
||||
strings (case doesn't matter) separated by either '-' or '+' characters and
|
||||
followed by the accelerator itself. The accelerator may be any alphanumeric
|
||||
character, any function key (from F1 to F12) or one of the special characters
|
||||
listed below (again, case doesn't matter):
|
||||
|
||||
DEL/DELETE Delete key
|
||||
INS/INSERT Insert key
|
||||
ENTER/RETURN Enter key
|
||||
PGUP PageUp key
|
||||
PGDN PageDown key
|
||||
LEFT Left cursor arrow key
|
||||
RIGHT Right cursor arrow key
|
||||
UP Up cursor arrow key
|
||||
DOWN Down cursor arrow key
|
||||
HOME Home key
|
||||
END End key
|
||||
SPACE Space
|
||||
TAB Tab key
|
||||
ESC/ESCAPE Escape key (Windows only)
|
||||
--]]
|
||||
function KSC(id, default)
|
||||
-- this is only for the rare case of someone assigning a complete list
|
||||
-- to ide.config.keymap.
|
||||
local keymap = ide.config.keymap
|
||||
return keymap[id] and "\t"..keymap[id] or default or ""
|
||||
end
|
||||
|
||||
@@ -4,12 +4,13 @@
|
||||
local ide = ide
|
||||
local frame = ide.frame
|
||||
local menuBar = frame.menuBar
|
||||
local notebook = frame.notebook
|
||||
local openDocuments = ide.openDocuments
|
||||
|
||||
local fileMenu = wx.wxMenu({
|
||||
{ ID_NEW, TR("&New")..KSC(ID_NEW), TR("Create an empty document") },
|
||||
{ ID_OPEN, TR("&Open...")..KSC(ID_OPEN), TR("Open an existing document") },
|
||||
{ ID_CLOSE, TR("&Close page")..KSC(ID_CLOSE), TR("Close the current editor window") },
|
||||
{ ID_CLOSE, TR("&Close Page")..KSC(ID_CLOSE), TR("Close the current editor window") },
|
||||
{ },
|
||||
{ ID_SAVE, TR("&Save")..KSC(ID_SAVE), TR("Save the current document") },
|
||||
{ ID_SAVEAS, TR("Save &As...")..KSC(ID_SAVEAS), TR("Save the current document to a file with a new name") },
|
||||
@@ -49,37 +50,22 @@ end
|
||||
frame:Connect(ID_NEW, wx.wxEVT_COMMAND_MENU_SELECTED, NewFile)
|
||||
frame:Connect(ID_OPEN, wx.wxEVT_COMMAND_MENU_SELECTED, OpenFile)
|
||||
frame:Connect(ID_SAVE, wx.wxEVT_COMMAND_MENU_SELECTED,
|
||||
function (event)
|
||||
function ()
|
||||
local editor = GetEditor()
|
||||
local id = editor:GetId()
|
||||
local filePath = openDocuments[id].filePath
|
||||
if (filePath) then
|
||||
SaveFile(editor, filePath)
|
||||
else
|
||||
SaveFileAs(editor)
|
||||
end
|
||||
SaveFile(editor, openDocuments[editor:GetId()].filePath)
|
||||
end)
|
||||
frame:Connect(ID_SAVE, wx.wxEVT_UPDATE_UI,
|
||||
function (event)
|
||||
local editor = GetEditor()
|
||||
local enabled = false
|
||||
if editor then
|
||||
local id = editor:GetId()
|
||||
enabled = openDocuments[id]
|
||||
and (openDocuments[id].isModified or not openDocuments[id].filePath)
|
||||
end
|
||||
event:Enable(enabled)
|
||||
event:Enable(EditorIsModified(GetEditor()))
|
||||
end)
|
||||
|
||||
frame:Connect(ID_SAVEAS, wx.wxEVT_COMMAND_MENU_SELECTED,
|
||||
function (event)
|
||||
local editor = GetEditor()
|
||||
SaveFileAs(editor)
|
||||
function ()
|
||||
SaveFileAs(GetEditor())
|
||||
end)
|
||||
frame:Connect(ID_SAVEAS, wx.wxEVT_UPDATE_UI,
|
||||
function (event)
|
||||
local editor = GetEditor()
|
||||
event:Enable(editor ~= nil)
|
||||
event:Enable(GetEditor() ~= nil)
|
||||
end)
|
||||
|
||||
frame:Connect(ID_SAVEALL, wx.wxEVT_COMMAND_MENU_SELECTED,
|
||||
@@ -100,7 +86,7 @@ frame:Connect(ID_SAVEALL, wx.wxEVT_UPDATE_UI,
|
||||
|
||||
frame:Connect(ID_CLOSE, wx.wxEVT_COMMAND_MENU_SELECTED,
|
||||
function (event)
|
||||
ClosePage() -- this will find the current editor
|
||||
ClosePage() -- this will find the current editor tab
|
||||
end)
|
||||
frame:Connect(ID_CLOSE, wx.wxEVT_UPDATE_UI,
|
||||
function (event)
|
||||
|
||||
@@ -72,6 +72,19 @@ menuBar:Append(debugMenu, TR("&Project"))
|
||||
-- Project directory handling
|
||||
|
||||
function ProjectUpdateProjectDir(projdir,skiptree)
|
||||
local dir = wx.wxFileName.DirName(projdir)
|
||||
|
||||
-- wxwidgets 2.9.x may report the last folder twice (depending on how the
|
||||
-- user selects the folder), which makes the selected folder incorrect.
|
||||
-- check if the last segment is repeated and drop it.
|
||||
if not wx.wxDirExists(projdir) then
|
||||
local dirs = dir:GetDirs()
|
||||
if #dirs > 1 and dirs[-1] == dirs[-2] then dir:RemoveLastDir() end
|
||||
if not wx.wxDirExists(dir:GetFullPath()) then return end
|
||||
end
|
||||
|
||||
projdir = dir:GetPath(wx.wxPATH_GET_VOLUME) -- no trailing slash
|
||||
|
||||
ide.config.path.projectdir = projdir ~= "" and projdir or nil
|
||||
frame:SetStatusText(projdir)
|
||||
if (not skiptree) then
|
||||
@@ -89,7 +102,7 @@ local function projChoose(event)
|
||||
local projectdir = ide.config.path.projectdir
|
||||
|
||||
local filePicker = wx.wxDirDialog(frame, TR("Choose a project directory"),
|
||||
projectdir ~= "" and projectdir or wx.wxGetCwd(),wx.wxFLP_USE_TEXTCTRL)
|
||||
projectdir ~= "" and projectdir or wx.wxGetCwd(), wx.wxDIRP_DIR_MUST_EXIST)
|
||||
if filePicker:ShowModal(true) == wx.wxID_OK then
|
||||
ProjectUpdateProjectDir(filePicker:GetPath())
|
||||
end
|
||||
|
||||
@@ -233,6 +233,11 @@ local function createenv ()
|
||||
end
|
||||
end
|
||||
|
||||
local os = { exit = function()
|
||||
ide.frame:AddPendingEvent(wx.wxCommandEvent(
|
||||
wx.wxEVT_COMMAND_MENU_SELECTED, ID_EXIT))
|
||||
end }
|
||||
env.os = setmetatable(os, {__index = _G.os})
|
||||
env.print = DisplayShell
|
||||
env.dofile = dofile
|
||||
env.loadfile = loadfile
|
||||
@@ -261,7 +266,7 @@ local function executeShellCode(tx)
|
||||
tx = tx:gsub("^%s*=%s*","")
|
||||
fn, err = loadstring("return "..tx)
|
||||
if not forceexpression and err and
|
||||
(err:find("'<eof>' expected near '") or
|
||||
(err:find("'?<eof>'? expected near '") or
|
||||
err:find("'%(' expected near") or
|
||||
err:find("unexpected symbol near '")) then
|
||||
fn, err = loadstring(tx)
|
||||
|
||||
@@ -50,13 +50,8 @@ if success then -- ok, server was started, we are solo
|
||||
svr:sendto(protocol.server.answerok,ip,port)
|
||||
local filename = msg:match(protocol.client.requestloading:gsub("%%s","(.+)$"))
|
||||
if filename then
|
||||
if LoadFile(filename, nil, true) then
|
||||
local frame = ide.frame
|
||||
frame:Iconize(false)
|
||||
frame:Raise()
|
||||
frame:Show(true)
|
||||
frame:SetFocus()
|
||||
frame:RequestUserAttention()
|
||||
if LoadFile(filename, nil, true)
|
||||
then RequestAttention()
|
||||
else DisplayOutput("Can't open requested file '"..filename.."'.\n") end
|
||||
end
|
||||
end
|
||||
|
||||
@@ -37,8 +37,8 @@ ide = {
|
||||
app = nil,
|
||||
},
|
||||
editor = {
|
||||
usetabs = true,
|
||||
autotabs = true,
|
||||
foldcompact = true,
|
||||
checkeol = true,
|
||||
},
|
||||
debugger = {
|
||||
verbose = false,
|
||||
@@ -240,13 +240,13 @@ end
|
||||
-- load specs
|
||||
local function loadSpecs(filter)
|
||||
for _, file in ipairs(FileSysGet("spec/*.*", wx.wxFILE)) do
|
||||
if file:match "%.lua$" and (filter or app.loadfilters.specs)(file) then
|
||||
if file:match("%.lua$") and (filter or app.loadfilters.specs)(file) then
|
||||
addToTab(ide.specs,file)
|
||||
end
|
||||
end
|
||||
|
||||
for _, spec in pairs(ide.specs) do
|
||||
spec.sep = spec.sep or ""
|
||||
spec.sep = spec.sep or "\1" -- default separator doesn't match anything
|
||||
spec.iscomment = {}
|
||||
spec.iskeyword0 = {}
|
||||
spec.isstring = {}
|
||||
|
||||
@@ -169,7 +169,14 @@ function FileSysGet(dir,spec)
|
||||
end
|
||||
local f = browse:FindFirst(dir,spec)
|
||||
while #f>0 do
|
||||
table.insert(content,(f:gsub("^file:",""))) -- remove file: protocol (wx2.9+)
|
||||
if f:match("^file:") then -- remove file: protocol (wx2.9+)
|
||||
f = f:gsub(ide.osname == "Windows" and "^file:/?" or "^file:","")
|
||||
:gsub('%%(%x%x)', function(n) return string.char(tonumber(n, 16)) end)
|
||||
end
|
||||
local file = wx.wxFileName(f)
|
||||
-- normalize path if possible to correct separators for the local FS
|
||||
table.insert(content,
|
||||
file:Normalize(wx.wxPATH_NORM_ALL) and file:GetFullPath() or f)
|
||||
f = browse:FindNext()
|
||||
end
|
||||
if ide.osname == 'Unix' then table.sort(content) end
|
||||
@@ -221,6 +228,8 @@ function FileCopy(file1, file2) return wx.wxCopyFile(file1, file2) end
|
||||
|
||||
TimeGet = pcall(require, "socket") and socket.gettime or os.clock
|
||||
|
||||
function isBinary(text) return text:find("[^\7\8\9\10\12\13\27\32-\255]") end
|
||||
|
||||
function pairsSorted(t, f)
|
||||
local a = {}
|
||||
for n in pairs(t) do table.insert(a, n) end
|
||||
@@ -235,6 +244,31 @@ function pairsSorted(t, f)
|
||||
return iter
|
||||
end
|
||||
|
||||
function fixUTF8(s, replacement)
|
||||
local p, len, invalid = 1, #s, {}
|
||||
while p <= len do
|
||||
if p == s:find("[%z\1-\127]", p) then p = p + 1
|
||||
elseif p == s:find("[\194-\223][\123-\191]", p) then p = p + 2
|
||||
elseif p == s:find( "\224[\160-\191][\128-\191]", p)
|
||||
or p == s:find("[\225-\236][\128-\191][\128-\191]", p)
|
||||
or p == s:find( "\237[\128-\159][\128-\191]", p)
|
||||
or p == s:find("[\238-\239][\128-\191][\128-\191]", p)
|
||||
or p == s:find( "\240[\144-\191][\128-\191]", p) then p = p + 3
|
||||
elseif p == s:find("[\241-\243][\128-\191][\128-\191][\128-\191]", p)
|
||||
or p == s:find( "\244[\128-\143][\128-\191][\128-\191]", p) then p = p + 4
|
||||
else
|
||||
s = s:sub(1, p-1)..replacement..s:sub(p+1)
|
||||
table.insert(invalid, p)
|
||||
end
|
||||
end
|
||||
return s, invalid
|
||||
end
|
||||
|
||||
function RequestAttention()
|
||||
local frame = ide.frame
|
||||
if not frame:IsActive() then frame:RequestUserAttention() end
|
||||
end
|
||||
|
||||
local messages, lang, counter
|
||||
function TR(msg, count)
|
||||
lang = lang or ide.config.language
|
||||
|
||||
@@ -6,10 +6,7 @@ api/opencl/*.lua
|
||||
api/glsl/*.lua
|
||||
api/cg/*.lua
|
||||
api/README
|
||||
cfg/user-sample.lua
|
||||
cfg/estrela.lua
|
||||
cfg/scheme-picker.lua
|
||||
cfg/tomorrow.lua
|
||||
cfg/*.lua
|
||||
cfg/i18n/*.lua
|
||||
interpreters/*.lua
|
||||
lualibs/copas/copas.lua
|
||||
@@ -66,7 +63,6 @@ src/editor/inspect.lua
|
||||
src/editor/iofilters.lua
|
||||
src/editor/keymap.lua
|
||||
src/editor/markup.lua
|
||||
src/editor/menu.lua
|
||||
src/editor/menu_edit.lua
|
||||
src/editor/menu_file.lua
|
||||
src/editor/menu_help.lua
|
||||
|
||||
@@ -17,19 +17,17 @@ local app = {
|
||||
createbitmap = CreateBitmap,
|
||||
loadfilters = {
|
||||
tools = function(file) return false end,
|
||||
specs = function(file) return file:find('^spec[/\\]lua%.lua$') end,
|
||||
specs = function(file) return file:find('spec[/\\]lua%.lua$') end,
|
||||
interpreters = function(file) return not file:find('estrela') end,
|
||||
},
|
||||
|
||||
postinit = function ()
|
||||
local bundle = wx.wxIconBundle()
|
||||
local files = FileSysGet("zbstudio/res/", wx.wxFILE)
|
||||
local files = FileSysGet("zbstudio/res/*.ico", wx.wxFILE)
|
||||
local icons = 0
|
||||
for i,file in ipairs(files) do
|
||||
if GetFileExt(file) == "ico" then
|
||||
icons = icons + 1
|
||||
bundle:AddIcon(file, wx.wxBITMAP_TYPE_ICO)
|
||||
end
|
||||
icons = icons + 1
|
||||
bundle:AddIcon(file, wx.wxBITMAP_TYPE_ICO)
|
||||
end
|
||||
if icons > 0 then ide.frame:SetIcons(bundle) end
|
||||
|
||||
|
||||
Reference in New Issue
Block a user