index 41a868f3f375e96cc13cf1a2f620aeb4073e3a3b..ea1f23660237da8593209739dc0200d84287843f 100644 (file)
Interface
- uses g_Basic, MAPDEF;
+ uses g_Basic, MAPDEF, Classes;
resourcestring
MsgNotAccessible = 'N/A';
MsgMsgChooseTexture = 'Select Texture';
MsgMsgChooseRes = 'Resource hasn''t been selected';
MsgMsgExit = 'Exit';
- MsgMsgExitPromt = 'Leaving so soon?';
+ MsgMsgExitPrompt = 'Leaving so soon?';
MsgMsgDelTexture = 'Delete the texture';
- MsgMsgDelTexturePromt = 'Delete the texture "%s" ?';
+ MsgMsgDelTexturePrompt = 'Delete the texture "%s" ?';
MsgMsgDelTextureCant = 'Can''t delete texture in use. Replace it on all panels with this texture.';
MsgMsgDelRecent = 'File does not longer exist';
- MsgMsgDelRecentPromt = 'Remove entry from recent list?';
+ MsgMsgDelRecentPrompt = 'Remove entry from recent list?';
MsgMsgClearMap = 'New map';
- MsgMsgClearMapPromt = 'Clear the entire map?';
+ MsgMsgClearMapPrompt = 'Clear the entire map?';
MsgMsgDeleteMap = 'Delete the map';
- MsgMsgDeleteMapPromt = 'Delete the map "%s" from "%s" ?';
+ MsgMsgDeleteMapPrompt = 'Delete the map "%s" from "%s" ?';
MsgMsgMapDeleted = 'Map is deleted';
- MsgMsgMapDeletedPromt = 'Map "%s" is deleted';
- MsgMsgReopenMapPromt = 'Reopen this map?';
+ MsgMsgMapDeletedPrompt = 'Map "%s" is deleted';
+ MsgMsgReopenMapPrompt = 'Reopen this map?';
MsgMsgExecError = 'Game start error';
MsgMsgSoundError = 'Can''t play sound';
MsgMsgWadError = 'Can''t open WAD: %s';
MsgHintWidth = 'Width: %d';
MsgHintHeight = 'Height: %d';
+ MsgMenuAppleAbout = 'About Editor';
+ MsgMenuApplePref = 'Preferences...';
+
MsgMenuFile = 'File';
MsgMenuFileNew = 'New';
MsgMenuFileOpen = 'Open...';
+ MsgMenuFileRecentMac = 'Open Recent';
+ MsgMenuFileRecentClearMac = 'Clear Recent';
MsgMenuFileSave = 'Save';
MsgMenuFileSaveAs = 'Save As...';
MsgMenuFileOpenWad = 'Select Map...';
MsgMenuFileReopen = 'Revert to Saved';
MsgMenuFileSaveMini = 'Save Minimap...';
- MsgMenuFileDelete = 'Delete from WAD...';
+ MsgMenuFileDelete = 'Remove from WAD...';
MsgMenuFilePackMap = 'Pack to WAD...';
- MsgMenuFileExit = 'Exit';
+ MsgMenuFileRecentWin = 'Recent Files';
+ MsgMenuFileExitWin = 'Exit';
MsgMenuEdit = 'Edit';
MsgMenuEditUndo = 'Undo';
MsgMenuEditCut = 'Cut';
MsgMenuEditPaste = 'Paste';
MsgMenuEditSelectAll = 'Select All';
+ MsgMenuEditSnapGrid = 'Snap to Grid';
+ MsgMenuEditStepGrid = 'Switch Grid Granularity';
MsgMenuEditToFore = 'Bring to Front';
MsgMenuEditToBack = 'Send to Back';
+ MsgMenuEditMapProps = 'Map Properties...';
+ MsgMenuEditPrefWin = 'Preferences...';
- MsgMenuTools = 'Tools';
- MsgMenuToolsSnapGrid = 'Snap to Grid';
- MsgMenuToolsMinimap = 'Show Minimap';
- MsgMenuToolsStepGrid = 'Switch Grid Granularity';
- MsgMenuToolsShowEdges = 'Show Map Bounds';
- MsgMenuToolsLayers = 'Layers';
+ MsgMenuView = 'View';
+ MsgMenuViewLayers = 'Layers';
+ MsgMenuViewMinimap = 'Show Minimap';
+ MsgMenuViewBounds = 'Show Map Bounds';
+ MsgMenuViewPreview = 'Preview Mode';
MsgMenuServ = 'Service';
MsgMenuServTest = 'Analyse Map...';
MsgMenuServOpt = 'Optimize Map...';
- MsgMenuServPreview = 'Preview Mode';
MsgMenuServLaunch = 'Run Test';
- MsgMenuSets = 'Settings';
- MsgMenuSetsMap = 'Map Properties...';
- MsgMenuSetsEditor = 'Preferences...';
- MsgMenuSetsLaunch = 'In-game test settings';
+ MsgMenuWindow = 'Window';
+ MsgMenuWindowMinimize = 'Minimize';
+ MsgMenuWindowZoom = 'Zoom';
MsgMenuHelp = 'Help';
- MsgMenuHelpAbout = 'About';
+ MsgMenuHelpAboutWin = 'About Editor';
MsgMenuLayerBack = '1. Background';
MsgMenuLayerWall = '2. Walls';
MsgCapOpt = 'Optimize Map';
MsgCapSets = 'Map Properties';
MsgCapLaunch = 'In-game test Settings';
- MsgCapEs = 'Editor Preferences';
+ MsgCapEs = 'Preferences';
MsgCapPack = 'Pack Map';
MsgCapSave = 'Save Map';
MsgCapMini = 'Save Minimap';
MsgCtrlSetsStats = 'Statistics:';
MsgCtrlSetsSizes = 'Map Size:';
+ MsgCtrlEsTesting = 'Testing';
MsgCtrlLaunchDm = 'Deathmatch';
MsgCtrlLaunchTdm = 'Team Deathmatch';
MsgCtrlLaunchCtf = 'Capture the Flag';
MsgCtrlLaunchClose = 'Close the game after exiting the map';
MsgCtrlLaunchOpen = 'Select Doom 2D: Forever executable';
+ MsgCtrlEsGeneral = 'General';
MsgCtrlEsGrid = 'Show Grid';
MsgCtrlEsTexture = 'Show Panel Texture';
MsgCtrlEsPanelSize = 'Show Panel Size';
MsgLabLaunchTime = 'Time Limit:';
MsgLabLaunchSecs = 'seconds';
MsgLabLaunchScore = 'Score Limit:';
- MsgLabLaunchPath = 'Path to Doom2DF.exe:';
+ MsgLabLaunchPathWin = 'Path to Doom2DF.exe:';
+ MsgLabLaunchPathMac = 'Path to Doom 2D Forever.app:';
+ MsgLabLaunchPathUnix = 'Path to Doom2DF:';
MsgLabLaunchArgs = 'Launch Arguments:';
MsgLabEsGrid = 'Grid Step:';
MsgLabEsMinimap = 'Mini-map Scale:';
MsgLabEsRecent = 'Recent Maps List Contains:';
MsgLabEsLanguage = 'Language:';
- MsgLabEsCompress = 'Compress archive when save';
- MsgLabEsBackup = 'Make backup before save';
+ MsgLabEsLanguageAuto = 'System Default';
+
+ MsgCtrlEsFiles = 'Files';
MsgLabPackSaveTo = 'Save to:';
MsgLabPackMapName = 'Map Resource Name:';
MsgWadSpecialMap = '<MAP WAD-FILE>';
MsgWadSpecialTexs = '<EXTRA TEXTURES>';
- MsgFileFilterAll = 'Doom 2D: Forever Maps (*.dfz, *.dfzip, *.zip, *.wad)|*.dfz;*.dfzip;*.zip;*.wad|Doom 2D: Forever 0.30 Maps (*.ini)|*.ini|All Files (*.*)|*.*';
- MsgFileFilterWad = 'Doom 2D: Forever Maps (*.dfz)|*.dfz|Doom 2D: Forever Maps (*.dfzip)|*.dfzip|Doom 2D: Forever Maps (*.zip)|*.zip|Doom 2D: Forever Maps (*.wad)|*.wad|All Files (*.*)|*.*';
+ MsgFileFilterAll = 'Doom 2D: Forever Maps (*.wad)|*.wad|Doom 2D: Forever 0.30 Maps (*.ini)|*.ini|All Files (*.*)|*.*';
+ MsgFileFilterWad = 'Doom 2D: Forever Maps (*.wad)|*.wad|All Files (*.*)|*.*';
+ MsgFileFilterExeMac = 'Doom 2D Forever.app|*.app|Doom 2D Forever (Unix Executable)|Doom2DF;*';
+ MsgFileFilterExeWin = 'Doom2DF.exe|Doom2DF.exe;*.exe';
+ MsgFileFilterExeUnix = 'Doom2DF|Doom2DF;*';
MsgEditorTitle = 'Doom 2D: Forever Map Editor';
AreaNames: Array [AREA_PLAYERPOINT1..AREA_BLUETEAMPOINT] of String;
TriggerNames: Array [TRIGGER_EXIT..TRIGGER_MAX] of String;
+function g_Language_GetList (): TStringList;
procedure g_Language_Set(lang: String);
Implementation
Uses
- gettext, g_options,
+ g_options, IniFiles, gettext, LazFileUtils,
SysUtils, e_log, f_main, f_about, f_activationtype,
f_addresource_sky, f_addresource_sound,
f_addresource_texture, f_choosetype, f_keys, f_mapcheck,
f_mapoptions, f_mapoptimization, f_options,
f_packmap, f_savemap, f_saveminimap, f_selectmap, Forms, utils;
+ const
+ InSourceLanguage = 'en_US';
+
procedure SetupArrays();
var
i: Integer;
end
else
Caption := FormCaption;
- // Главное меню:
- // "Файл":
+
+ // Apple menu:
+ miAppleAbout.Caption := MsgMenuAppleAbout;
+ miApplePref.Caption := MsgMenuApplePref;
+ // File menu:
miMenuFile.Caption := MsgMenuFile;
miNewMap.Caption := MsgMenuFileNew;
miOpenMap.Caption := MsgMenuFileOpen;
+ miMacRecentSubMenu.Caption := MsgMenuFileRecentMac;
+ miMacRecentClear.Caption := MsgMenuFileRecentClearMac;
miSaveMap.Caption := MsgMenuFileSave;
miSaveMapAs.Caption := MsgMenuFileSaveAs;
miOpenWadMap.Caption := MsgMenuFileOpenWad;
miSaveMiniMap.Caption := MsgMenuFileSaveMini;
miDeleteMap.Caption := MsgMenuFileDelete;
miPackMap.Caption := MsgMenuFilePackMap;
- miExit.Caption := MsgMenuFileExit;
- // "Правка":
+ miWinRecent.Caption := MsgMenuFileRecentWin;
+ miExit.Caption := MsgMenuFileExitWin;
+ // Edit menu:
miMenuEdit.Caption := MsgMenuEdit;
miUndo.Caption := MsgMenuEditUndo;
miCopy.Caption := MsgMenuEditCopy;
miCut.Caption := MsgMenuEditCut;
miPaste.Caption := MsgMenuEditPaste;
miSelectAll.Caption := MsgMenuEditSelectAll;
+ miSnapToGrid.Caption := MsgMenuEditSnapGrid;
+ miSwitchGrid.Caption := MsgMenuEditStepGrid;
miToFore.Caption := MsgMenuEditToFore;
miToBack.Caption := MsgMenuEditToBack;
- // "Инструменты":
- miSnapToGrid.Caption := MsgMenuToolsSnapGrid;
- miMiniMap.Caption := MsgMenuToolsMinimap;
- miSwitchGrid.Caption := MsgMenuToolsStepGrid;
- miShowEdges.Caption := MsgMenuToolsShowEdges;
- miLayers.Caption := MsgMenuToolsLayers;
+ miMapOptions.Caption := MsgMenuEditMapProps;
+ miOptions.Caption := MsgMenuEditPrefWin;
+ // View menu:
+ miMenuView.Caption := MsgMenuView;
+ miLayers.Caption := MsgMenuViewLayers;
miLayer1.Caption := MsgMenuLayerBack;
miLayer2.Caption := MsgMenuLayerWall;
miLayer3.Caption := MsgMenuLayerFore;
miLayer7.Caption := MsgMenuLayerMonster;
miLayer8.Caption := MsgMenuLayerArea;
miLayer9.Caption := MsgMenuLayerTrigger;
- miMapOptions.Caption := MsgMenuSetsMap;
- miOptions.Caption := MsgMenuSetsEditor;
- // "Сервис":
+ miMiniMap.Caption := MsgMenuViewMinimap;
+ miShowEdges.Caption := MsgMenuViewBounds;
+ miMapPreview.Caption := MsgMenuViewPreview;
+ // Service menu:
miMenuService.Caption := MsgMenuServ;
miCheckMap.Caption := MsgMenuServTest;
miOptimmization.Caption := MsgMenuServOpt;
- miMapPreview.Caption := MsgMenuServPreview;
miTestMap.Caption := MsgMenuServLaunch;
- // "Справка":
+ // Window menu:
+ miMenuWindow.Caption := MsgMenuWindow;
+ miMacMinimize.Caption := MsgMenuWindowMinimize;
+ miMacZoom.Caption := MsgMenuWindowZoom;
+ // Help menu:
miMenuHelp.Caption := MsgMenuHelp;
- miAbout.Caption := MsgMenuHelpAbout;
+ miAbout.Caption := MsgMenuHelpAboutWin;
- // Панель инструментов:
+ // Toolbar:
tbNewMap.Hint := MsgMenuTbNew;
tbOpenMap.Hint := MsgMenuTbOpen;
tbSaveMap.Hint := MsgMenuTbSave;
tbOpenWadMap.Hint := MsgMenuTbOpenWad;
tbShowMap.Hint := MsgMenuTbMinimap;
tbShow.Hint := MsgMenuTbLayers;
- tbGridOn.Hint := MsgMenuTbGrid;
- tbGrid.Hint := MsgMenuTbGridStep;
- tbTestMap.Hint := MsgMenuTbLaunch;
- // Всплывающее меню для кнопки слоев:
miLayerP1.Caption := MsgMenuLayerBack;
miLayerP2.Caption := MsgMenuLayerWall;
miLayerP3.Caption := MsgMenuLayerFore;
miLayerP7.Caption := MsgMenuLayerMonster;
miLayerP8.Caption := MsgMenuLayerArea;
miLayerP9.Caption := MsgMenuLayerTrigger;
+ tbGridOn.Hint := MsgMenuTbGrid;
+ tbGrid.Hint := MsgMenuTbGridStep;
+ tbTestMap.Hint := MsgMenuTbLaunch;
- // Кнопка применения свойств:
+ // Object property editor:
bApplyProperty.Caption := MsgBtnApplyProps;
- // Редактор свойств объектов:
vleObjectProperty.TitleCaptions[0] := MsgCtrlPropKey;
vleObjectProperty.TitleCaptions[1] := MsgCtrlPropValue;
- // Вкладка "Панели":
+ // Panels Tab:
tsPanels.Caption := MsgCtrlPanels;
lbPanelType.Hint := MsgPropPanelType;
lbTextureList.Hint := MsgCtrlListTexture;
- // Панель настройки текстур:
LabelTxW.Caption := MsgLabTexWidth;
LabelTxH.Caption := MsgLabTexHeight;
cbPreview.Caption := MsgCtrlPreview;
bbRemoveTexture.Hint := MsgBtnTextureDelete;
bClearTexture.Hint := MsgBtnTextureEmpty;
- // Вкладка "Предметы":
+ // Items Tab:
tsItems.Caption := MsgCtrlItems;
lbItemList.Hint := MsgCtrlListItem;
cbOnlyDM.Caption := MsgCtrlItemDm;
cbFall.Caption := MsgCtrlItemFalls;
- // Вкладка "Монстры":
+ // Monters Tab:
tsMonsters.Caption := MsgCtrlMonsters;
lbMonsterList.Hint := MsgCtrlListMonster;
rbMonsterLeft.Caption := MsgCtrlLeft;
rbMonsterRight.Caption := MsgCtrlRight;
- // Вкладка "Области":
+ // Areas Tab:
tsAreas.Caption := MsgCtrlAreas;
lbAreasList.Hint := MsgCtrlListArea;
rbAreaLeft.Caption := MsgCtrlLeft;
rbAreaRight.Caption := MsgCtrlRight;
- // Вкладка "Триггеры":
+ // Triggers Tab:
tsTriggers.Caption := MsgCtrlTriggers;
lbTriggersList.Hint := MsgCtrlListTrigger;
clbActivationType.Hint := MsgCtrlListActive;
bCancel.Caption := MsgBtnCancel;
end;
-// From "Editor settings":
+// Form preferences:
with OptionsForm do
begin
Caption := MsgCapEs;
bOK.Caption := MsgBtnOk;
bCancel.Caption := MsgBtnCancel;
// TabGeneral:
+ TabGeneral.Caption := MsgCtrlEsGeneral;
cbShowDots.Caption := MsgCtrlEsGrid;
cbShowTexture.Caption := MsgCtrlEsTexture;
cbShowSize.Caption := MsgCtrlEsPanelSize;
LabelMinimap.Caption := MsgLabEsMinimap;
LabelLanguage.Caption := MsgLabEsLanguage;
// TabFiles:
- cbCompress.Caption := MsgLabEsCompress;
- cbBackup.Caption := MsgLabEsBackup;
+ TabFiles.Caption := MsgCtrlEsFiles;
LabelRecent.Caption := MsgLabEsRecent;
// TabTesting:
+ TabTesting.Caption := MsgCtrlEsTesting;
rbDM.Caption := MsgCtrlLaunchDm;
rbTDM.Caption := MsgCtrlLaunchTdm;
rbCTF.Caption := MsgCtrlLaunchCtf;
LabelTime.Caption := MsgLabLaunchTime;
LabelSecs.Caption := MsgLabLaunchSecs;
LabelScore.Caption := MsgLabLaunchScore;
- LabelPath.Caption := MsgLabLaunchPath;
- FindD2dDialog.Title := MsgCtrlLaunchOpen;
+ {$IF DEFINED(DARWIN)}
+ LabelPath.Caption := MsgLabLaunchPathMac;
+ ExeEdit.DialogTitle := MsgCtrlLaunchOpen;
+ ExeEdit.Filter := MsgFileFilterExeMac;
+ {$ELSEIF DEFINED(WINDOWS)}
+ LabelPath.Caption := MsgLabLaunchPathWin;
+ ExeEdit.DialogTitle := MsgCtrlLaunchOpen;
+ ExeEdit.Filter := MsgFileFilterExeWin;
+ {$ELSE}
+ LabelPath.Caption := MsgLabLaunchPathUnix;
+ ExeEdit.DialogTitle := MsgCtrlLaunchOpen;
+ ExeEdit.Filter := MsgFileFilterExeUnix;
+ {$ENDIF}
LabelArgs.Caption := MsgLabLaunchArgs;
end;
Application.Title := MsgEditorTitle;
end;
-procedure g_Language_Set(lang: String);
- const langfilename = 'editor';
- var syslang, fallbacklang: String;
+type
+ TResArg = record
+ ini: TIniFile;
+ ignored: TStringList;
+ end;
+ PResArg = ^TResArg;
+
+function gResourceItarator (name, value: AnsiString; hash: LongInt; arg: Pointer): AnsiString;
+ var res: PResArg; orig: AnsiString;
begin
- e_WriteLog('g_Language_Set: requested lang is "' + lang + '"', MSG_NOTIFY);
- GetLanguageIDs(syslang, fallbacklang);
- if lang = '' then lang := syslang;
+ res := PResArg(arg);
+ orig := res.ini.ReadString('resourcestring', name + '$', '');
+ if (orig = '') or (orig = value) then
+ begin
+ if res.ini.ValueExists('resourcestring', name) then
+ begin
+ result := res.ini.ReadString('resourcestring', name, '');
+ end
+ else
+ begin
+ result := value;
+ if res.ignored.IndexOf(Copy(name, 1, Pos('.', name) - 1)) < 0 then
+ e_WriteLog(' Seems that key ' + name + ' not translated', MSG_NOTIFY);
+ end;
+ end
+ else
+ begin
+ e_WriteLog(' Original resource string for ' + name + ' do not match, translation are outdated?', MSG_WARNING);
+ e_WriteLog(' [' + value + '] -> [' + orig + ']', MSG_WARNING);
+ result := value;
+ end;
+end;
- ResetResourceTables;
+procedure gSetLanguageFormStream (const lang: AnsiString; stream: TStream; out ok: Boolean);
+ var res: TResArg;
+begin
+ ok := False;
try
- e_WriteLog('g_Language_Set: try language "' + lang + '"', MSG_NOTIFY);
- TranslateResourceStrings(LangDir + DirectorySeparator + langfilename + '.' + lang + '.mo');
+ res.ini := TIniFile.Create(stream, [ifoStripComments, ifoStripQuotes, ifoEscapeLineFeeds]);
except
+ res.ini := nil;
+ end;
+ if res.ini <> nil then
+ begin
try
- e_WriteLog('g_Language_Set: try system language "' + syslang + '"', MSG_NOTIFY);
- TranslateResourceStrings(LangDir + DirectorySeparator + langfilename + '.' + syslang + '.mo');
- except
- try
- e_WriteLog('g_Language_Set: try fallback language "' + fallbacklang + '"', MSG_NOTIFY);
- TranslateResourceStrings(LangDir + DirectorySeparator + langfilename + '.' + fallbacklang + '.mo');
- except
- e_WriteLog('g_Language_Set: use default strings', MSG_NOTIFY);
+ ok := res.ini.SectionExists('resourcestring');
+ if ok then
+ begin
+ res.ignored := TStringList.Create;
+ res.ignored.CaseSensitive := False;
+ res.ini.ReadSection('ignore', res.ignored);
+ res.ignored.Sort;
+ SetResourceStrings(gResourceItarator, @res);
+ res.ignored.Free();
end;
+ finally
+ res.ini.Free();
end;
end;
- e_WriteLog('g_Language_Set: ok', MSG_NOTIFY);
+ if not ok then e_WriteLog('Translation file for ' + lang + ' are invalid ', MSG_FATALERROR);
+end;
+
+procedure gSetLanguageFromFile (const lang: AnsiString; out ok: Boolean);
+ const langfilename = 'editor';
+ var stream: TFileStream; name: AnsiString;
+begin
+ name := LangDir + DirectorySeparator + langfilename + '.' + lang + '.lng';
+ try
+ stream := TFileStream.Create(name, fmOpenRead);
+ try
+ gSetLanguageFormStream(lang, stream, ok);
+ finally
+ stream.Free();
+ end;
+ except on E: EFOpenError do
+ ok := False;
+ end;
+end;
+
+procedure gSetLanguage (const lang: AnsiString; out ok: Boolean);
+begin
+ gSetLanguageFromFile(lang, ok);
+end;
+
+function g_Language_GetList (): TStringList;
+ const langfilename = 'editor';
+ var list: TStringList; info: TSearchRec;
+begin
+ list := TStringList.Create;
+ list.Duplicates := dupIgnore;
+ list.Add(InSourceLanguage);
+ if FindFirst(LangDir + DirectorySeparator + langfilename + '.*.lng', faAnyFile, info) = 0 then
+ begin
+ repeat
+ list.Add(Copy(ExtractFileNameWithoutExt(info.Name), Length(langfilename) + 2));
+ until FindNext(info) <> 0;
+ FindClose(info);
+ end;
+ list.Sort;
+ result := list;
+end;
+
+procedure g_Language_Set(lang: String);
+ var syslang, fallbacklang: String; ok: Boolean;
+begin
+ ResetResourceTables;
+
+ if lang = '' then
+ begin
+ GetLanguageIDs(syslang, fallbacklang); // TODO: remove dependency on gettext
+ e_WriteLog('g_Language_Set: try strings "' + syslang + '" (system)', MSG_NOTIFY);
+ gSetLanguage(syslang, ok);
+ if not ok then
+ begin
+ e_WriteLog('g_Language_Set: try strings "' + fallbacklang + '" (fallback)', MSG_NOTIFY);
+ gSetLanguage(syslang, ok);
+ end;
+ end
+ else
+ begin
+ e_WriteLog('g_Language_Set: try strings "' + lang + '" (user specified)', MSG_NOTIFY);
+ gSetLanguage(lang, ok);
+ end;
+ if not ok then e_WriteLog('g_Language_Set: use default strings "' + InSourceLanguage + '" (in-source)', MSG_NOTIFY);
+
SetupArrays();
SetupCaptions();
RemoveSelectFromObjects();