OpenClonk
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Properties Friends Macros
C4Language Class Reference

#include <C4Language.h>

Public Member Functions

 C4Language ()
 
 ~C4Language ()
 
bool CloseGroup (const char *strPath)
 
void ClearLanguage ()
 
bool Init ()
 
void Clear ()
 
int GetPackCount ()
 
C4GroupSet GetPackGroups (C4Group &)
 
int GetInfoCount ()
 
C4LanguageInfoGetInfo (int iIndex)
 
C4LanguageInfoFindInfo (const char *strCode)
 
bool LoadLanguage (const char *strLanguages)
 
bool HasStringTable () const
 

Static Public Member Functions

static bool LoadComponentHost (C4ComponentHost *host, C4Group &hGroup, const char *szFilename, const char *szLanguage)
 

Detailed Description

Definition at line 40 of file C4Language.h.

Constructor & Destructor Documentation

C4Language::C4Language ( )

Definition at line 47 of file C4Language.cpp.

48 {
49  Infos = nullptr;
50  PackGroupLocation[0] = 0;
51 }
C4Language::~C4Language ( )

Definition at line 53 of file C4Language.cpp.

References Clear().

54 {
55  Clear();
56 }
void Clear()
Definition: C4Language.cpp:117

Here is the call graph for this function:

Member Function Documentation

void C4Language::Clear ( )

Definition at line 117 of file C4Language.cpp.

References C4GroupSet::Clear(), and C4Group::Close().

Referenced by C4Application::Clear(), Init(), and ~C4Language().

118 {
119  // Clear pack groups
120  PackGroups.Clear();
121  // Clear packs
122  Packs.Clear();
123  // Close pack directory
124  PackDirectory.Close();
125  // Clear infos
126  C4LanguageInfo* pNext;
127  while (Infos)
128  {
129  pNext = Infos->Next;
130  delete Infos;
131  Infos = pNext;
132  }
133  Infos = nullptr;
134 }
bool Close()
Definition: C4Group.cpp:755
void Clear()
Definition: C4GroupSet.cpp:52

Here is the call graph for this function:

Here is the caller graph for this function:

void C4Language::ClearLanguage ( )

Definition at line 413 of file C4Language.cpp.

References C4ComponentHost::Clear(), and C4LangStringTable::GetSystemStringTable().

Referenced by C4Application::Clear(), and LoadLanguage().

414 {
415  // Clear resource string table
417 }
static C4LangStringTable & GetSystemStringTable()

Here is the call graph for this function:

Here is the caller graph for this function:

bool C4Language::CloseGroup ( const char *  strPath)

Definition at line 421 of file C4Language.cpp.

References StdStrBuf::getData(), C4Group::GetFullName(), C4GroupSet::GetGroup(), ItemIdentical(), and C4GroupSet::UnregisterGroup().

422 {
423  // Check all open language packs
424  C4Group *pPack;
425  for (int iPack = 0; (pPack = Packs.GetGroup(iPack)); iPack++)
426  if (ItemIdentical(strPath, pPack->GetFullName().getData()))
427  {
428  Packs.UnregisterGroup(iPack);
429  return true;
430  }
431  // No pack of that path
432  return false;
433 }
const char * getData() const
Definition: StdBuf.h:450
bool ItemIdentical(const char *szFilename1, const char *szFilename2)
Definition: StdFile.cpp:865
bool UnregisterGroup(int32_t iIndex)
Definition: C4GroupSet.cpp:276
StdStrBuf GetFullName() const
Definition: C4Group.cpp:2078
C4Group * GetGroup(int32_t iIndex)
Definition: C4GroupSet.cpp:261

Here is the call graph for this function:

C4LanguageInfo * C4Language::FindInfo ( const char *  strCode)

Definition at line 356 of file C4Language.cpp.

References C4LanguageInfo::Code, and SEqualNoCase().

357 {
358  for (C4LanguageInfo *pInfo = Infos; pInfo; pInfo = pInfo->Next)
359  if (SEqualNoCase(pInfo->Code, strCode, 2))
360  return pInfo;
361  return nullptr;
362 }
bool SEqualNoCase(const char *szStr1, const char *szStr2, int iLen)
Definition: Standard.cpp:177

Here is the call graph for this function:

C4LanguageInfo * C4Language::GetInfo ( int  iIndex)

Definition at line 346 of file C4Language.cpp.

347 {
348  for (C4LanguageInfo *pInfo = Infos; pInfo; pInfo = pInfo->Next)
349  if (iIndex <= 0)
350  return pInfo;
351  else
352  iIndex--;
353  return nullptr;
354 }
int C4Language::GetInfoCount ( )

Definition at line 141 of file C4Language.cpp.

142 {
143  int iCount = 0;
144  for (C4LanguageInfo *pInfo = Infos; pInfo; pInfo = pInfo->Next)
145  iCount++;
146  return iCount;
147 }
int C4Language::GetPackCount ( )

Definition at line 136 of file C4Language.cpp.

References C4GroupSet::GetGroupCount().

137 {
138  return Packs.GetGroupCount();
139 }
int32_t GetGroupCount()
Definition: C4GroupSet.cpp:253

Here is the call graph for this function:

C4GroupSet C4Language::GetPackGroups ( C4Group hGroup)

Definition at line 151 of file C4Language.cpp.

References _MAX_FNAME, _MAX_PATH, C4Config::AtRelativePath(), C4GSCnt_Component, C4GSCnt_Language, C4Game::C4S, C4Group::Close(), Config, DirectorySeparator, Game, StdStrBuf::getData(), GetExtension(), C4Group::GetFullName(), C4GroupSet::GetGroup(), StdStrBuf::getLength(), GetRelativePathS(), C4Scenario::Head, C4Group::OpenAsChild(), C4Group::OpenChild(), C4Group::OpenMother(), C4SHead::Origin, C4GroupSet::RegisterGroup(), C4GroupSet::RegisterGroups(), SAppend(), SAppendChar(), C4Game::ScenarioFilename, SCopy(), SEqualNoCase(), and SLen().

Referenced by LoadComponentHost().

152 {
153  // Build a group set containing the provided group and
154  // alternative groups for cross-loading from a language pack
155  char strRelativePath[_MAX_PATH + 1];
156  char strTargetLocation[_MAX_PATH + 1];
157  char strPackPath[_MAX_PATH + 1];
158  char strPackGroupLocation[_MAX_PATH + 1];
159  char strAdvance[_MAX_PATH + 1];
160 
161  // Store wanted target location
162  SCopy(Config.AtRelativePath(hGroup.GetFullName().getData()), strRelativePath, _MAX_PATH);
163  SCopy(strRelativePath, strTargetLocation, _MAX_PATH);
164 
165  // Adjust location by scenario origin
167  {
168  const char *szScenarioRelativePath = GetRelativePathS(strRelativePath, Config.AtRelativePath(Game.ScenarioFilename));
169  if (szScenarioRelativePath != strRelativePath)
170  {
171  // this is a path within the scenario! Change to origin.
172  size_t iRestPathLen = SLen(szScenarioRelativePath);
173  if (Game.C4S.Head.Origin.getLength() + 1 + iRestPathLen <= _MAX_PATH)
174  {
175  SCopy(Game.C4S.Head.Origin.getData(), strTargetLocation);
176  if (iRestPathLen)
177  {
178  SAppendChar(DirectorySeparator, strTargetLocation);
179  SAppend(szScenarioRelativePath, strTargetLocation);
180  }
181  }
182  }
183  }
184 
185  // Process all language packs (and their respective pack groups)
186  C4Group *pPack, *pPackGroup;
187  for (int iPack = 0; (pPack = Packs.GetGroup(iPack)) && (pPackGroup = PackGroups.GetGroup(iPack)); iPack++)
188  {
189  // Get current pack group position within pack
190  SCopy(pPack->GetFullName().getData(), strPackPath, _MAX_PATH);
191  GetRelativePath(pPackGroup->GetFullName().getData(), strPackPath, strPackGroupLocation);
192 
193  // Pack group is at correct position within pack: continue with next pack
194  if (SEqualNoCase(strPackGroupLocation, strTargetLocation))
195  continue;
196 
197  // Try to backtrack until we can reach the target location as a relative child
198  while ( strPackGroupLocation[0]
199  && !GetRelativePath(strTargetLocation, strPackGroupLocation, strAdvance)
200  && pPackGroup->OpenMother() )
201  {
202  // Update pack group location
203  GetRelativePath(pPackGroup->GetFullName().getData(), strPackPath, strPackGroupLocation);
204  }
205 
206  // We can reach the target location as a relative child
207  if (strPackGroupLocation[0] && GetRelativePath(strTargetLocation, strPackGroupLocation, strAdvance))
208  {
209  // Advance pack group to relative child
210  pPackGroup->OpenChild(strAdvance);
211  }
212 
213  // Cannot reach by advancing: need to close and reopen (rewinding group file)
214  else
215  {
216  // Close pack group (if it is open at all)
217  pPackGroup->Close();
218  // Reopen pack group to relative position in language pack if possible
219  pPackGroup->OpenAsChild(pPack, strTargetLocation);
220  }
221 
222  }
223 
224  // Store new target location
225  SCopy(strTargetLocation, PackGroupLocation, _MAX_FNAME);
226 
227  C4GroupSet r;
228  // Provided group gets highest priority
229  r.RegisterGroup(hGroup, false, 1000, C4GSCnt_Component);
230  // register currently open pack groups
231  r.RegisterGroups(PackGroups, C4GSCnt_Language);
232  return r;
233 }
const char * getData() const
Definition: StdBuf.h:450
StdCopyStrBuf Origin
Definition: C4Scenario.h:80
char ScenarioFilename[_MAX_PATH+1]
Definition: C4Game.h:104
C4Config Config
Definition: C4Config.cpp:837
void SCopy(const char *szSource, char *sTarget, size_t iMaxL)
Definition: Standard.cpp:122
void SAppendChar(char cChar, char *szStr)
Definition: Standard.cpp:235
bool RegisterGroup(C4Group &rGroup, bool fOwnGrp, int32_t Priority, int32_t Contents, bool fCheckContent=true)
Definition: C4GroupSet.cpp:90
void SAppend(const char *szSource, char *szTarget, int iMaxL)
Definition: Standard.cpp:227
C4Game Game
Definition: C4Globals.cpp:52
C4Scenario C4S
Definition: C4Game.h:76
#define C4GSCnt_Component
Definition: C4GroupSet.h:41
bool SEqualNoCase(const char *szStr1, const char *szStr2, int iLen)
Definition: Standard.cpp:177
bool RegisterGroups(const C4GroupSet &rCopy, int32_t Contents, const char *szFilename=nullptr, int32_t iMaxSkipID=0)
Definition: C4GroupSet.cpp:130
#define _MAX_PATH
size_t SLen(const char *sptr)
Definition: Standard.h:78
bool OpenMother()
Definition: C4Group.cpp:2197
StdStrBuf GetFullName() const
Definition: C4Group.cpp:2078
bool Close()
Definition: C4Group.cpp:755
#define _MAX_FNAME
bool OpenChild(const char *strEntry)
Definition: C4Group.cpp:2161
char * GetExtension(char *szFilename)
Definition: StdFile.cpp:131
#define C4GSCnt_Language
Definition: C4GroupSet.h:40
size_t getLength() const
Definition: StdBuf.h:453
C4SHead Head
Definition: C4Scenario.h:230
const char * AtRelativePath(const char *szFilename)
Definition: C4Config.cpp:660
#define DirectorySeparator
bool OpenAsChild(C4Group *pMother, const char *szEntryName, bool fExclusive=false, bool fCreate=false)
Definition: C4Group.cpp:1585
const char * GetRelativePathS(const char *strPath, const char *strRelativeTo)
Definition: StdFile.cpp:221
C4Group * GetGroup(int32_t iIndex)
Definition: C4GroupSet.cpp:261

Here is the call graph for this function:

Here is the caller graph for this function:

bool C4Language::HasStringTable ( ) const
inline

Definition at line 70 of file C4Language.h.

References C4ComponentHost::GetDataBuf(), C4LangStringTable::GetSystemStringTable(), and StdStrBuf::isNull().

Referenced by C4Application::Clear(), C4Game::Clear(), and C4Application::DoInit().

const StdStrBuf & GetDataBuf() const
static C4LangStringTable & GetSystemStringTable()
bool isNull() const
Definition: StdBuf.h:449

Here is the call graph for this function:

Here is the caller graph for this function:

bool C4Language::Init ( )

Definition at line 58 of file C4Language.cpp.

References _MAX_FNAME, C4Reloc::begin(), C4CFN_Languages, C4Group_UnpackDirectory(), C4GSCnt_Language, C4GSPrio_Base, Clear(), StdStrBuf::Copy(), DirectoryExists(), DirSep, C4Reloc::end(), C4Group::FindNextEntry(), StdStrBuf::getData(), C4GroupSet::GetGroup(), ItemExists(), C4Group::Open(), C4GroupSet::RegisterGroup(), Reloc, and sprintf.

Referenced by C4Application::DoInit().

59 {
60  // Clear (to allow clean re-init)
61  Clear();
62 
63  // Make sure Language.ocg is unpacked (TODO: This won't work properly if Language.ocg is in system data path)
64  // Assume for now that Language.ocg is either at a writable location or unpacked already.
65  // TODO: Use all Language.c4gs that we find, and merge them.
66  // TODO: Use gettext instead?
67  StdStrBuf langPath;
68  C4Reloc::iterator iter;
69  for(iter = Reloc.begin(); iter != Reloc.end(); ++iter)
70  {
71  langPath.Copy((*iter).strBuf + DirSep + C4CFN_Languages);
72  if(ItemExists(langPath.getData()))
73  {
74  if(DirectoryExists(langPath.getData()))
75  break;
76  if(C4Group_UnpackDirectory(langPath.getData()))
77  break;
78  }
79  }
80 
81  // Break if no language.ocg found
82  if(iter != Reloc.end())
83  {
84  // Look for available language packs in Language.ocg
85  C4Group *pPack;
86  char strPackFilename[_MAX_FNAME + 1], strEntry[_MAX_FNAME + 1];
87  if (PackDirectory.Open(langPath.getData()))
88  {
89  while (PackDirectory.FindNextEntry("*.ocg", strEntry))
90  {
91  sprintf(strPackFilename, "%s" DirSep "%s", C4CFN_Languages, strEntry);
92  pPack = new C4Group();
93  if (pPack->Open(strPackFilename))
94  {
95  Packs.RegisterGroup(*pPack, true, C4GSCnt_Language, false);
96  }
97  else
98  {
99  delete pPack;
100  }
101  }
102  }
103 
104  // Now create a pack group for each language pack (these pack groups are child groups
105  // that browse along each pack to access requested data)
106  for (int iPack = 0; (pPack = Packs.GetGroup(iPack)); iPack++)
107  PackGroups.RegisterGroup(*(new C4Group), true, C4GSPrio_Base, C4GSCnt_Language);
108  }
109 
110  // Load language infos by scanning string tables (the engine doesn't really need this at the moment)
111  InitInfos();
112 
113  // Done
114  return true;
115 }
const char * getData() const
Definition: StdBuf.h:450
bool RegisterGroup(C4Group &rGroup, bool fOwnGrp, int32_t Priority, int32_t Contents, bool fCheckContent=true)
Definition: C4GroupSet.cpp:90
#define sprintf
Definition: Standard.h:171
PathList::const_iterator iterator
Definition: C4Reloc.h:38
bool C4Group_UnpackDirectory(const char *szFilename)
Definition: C4Group.cpp:306
#define C4CFN_Languages
Definition: C4Components.h:32
bool Open(const char *szGroupName, bool fCreate=false)
Definition: C4Group.cpp:514
#define _MAX_FNAME
iterator begin() const
Definition: C4Reloc.cpp:59
C4Reloc Reloc
Definition: C4Reloc.cpp:22
bool DirectoryExists(const char *szFilename)
Definition: StdFile.cpp:694
bool FindNextEntry(const char *szWildCard, StdStrBuf *sFileName=nullptr, size_t *iSize=nullptr, bool fStartAtFilename=false)
Definition: C4Group.cpp:1780
#define C4GSCnt_Language
Definition: C4GroupSet.h:40
iterator end() const
Definition: C4Reloc.cpp:64
void Clear()
Definition: C4Language.cpp:117
#define DirSep
bool ItemExists(const char *szItemName)
Definition: StdFile.h:75
void Copy()
Definition: StdBuf.h:475
#define C4GSPrio_Base
Definition: C4GroupSet.h:23
C4Group * GetGroup(int32_t iIndex)
Definition: C4GroupSet.cpp:261

Here is the call graph for this function:

Here is the caller graph for this function:

bool C4Language::LoadComponentHost ( C4ComponentHost host,
C4Group hGroup,
const char *  szFilename,
const char *  szLanguage 
)
static

Definition at line 235 of file C4Language.cpp.

References GetPackGroups(), Languages, and C4ComponentHost::Load().

Referenced by C4ScenarioListLoader::SubFolder::DoLoadContents(), C4RankSystem::Load(), C4ScenarioListLoader::Entry::Load(), C4MapFolderData::Load(), C4Game::LoadAdditionalSystemGroup(), C4ScenarioListLoader::Scenario::LoadCustomPre(), C4Game::OpenScenario(), and C4Game::UpdateLanguage().

236 {
237  assert(host);
238  if (!host) return false;
239  C4GroupSet hGroups = ::Languages.GetPackGroups(hGroup);
240  return host->Load(hGroups, szFilename, szLanguage);
241 }
bool Load(C4Group &hGroup, const char *szFilename, const char *szLanguage=nullptr)
C4GroupSet GetPackGroups(C4Group &)
Definition: C4Language.cpp:151
C4Language Languages
Definition: C4Language.cpp:45

Here is the call graph for this function:

Here is the caller graph for this function:

bool C4Language::LoadLanguage ( const char *  strLanguages)

Definition at line 364 of file C4Language.cpp.

References ClearLanguage(), Log(), and SCopySegment().

Referenced by C4Application::DoInit().

365 {
366  // Clear old string table
367  ClearLanguage();
368  // Try to load string table according to language sequence
369  char strLanguageCode[2 + 1];
370  for (int i = 0; SCopySegment(strLanguages, i, strLanguageCode, ',', 2, true); i++)
371  if (InitStringTable(strLanguageCode))
372  return true;
373  // No matching string table found: hardcoded fallback to US
374  if (InitStringTable("US"))
375  return true;
376  // No string table present: this is really bad
377  Log("Error loading language string table.");
378  return false;
379 }
bool SCopySegment(const char *szString, int iSegment, char *sTarget, char cSeparator, int iMaxL, bool fSkipWhitespace)
Definition: Standard.cpp:243
void ClearLanguage()
Definition: C4Language.cpp:413
bool Log(const char *szMessage)
Definition: C4Log.cpp:195

Here is the call graph for this function:

Here is the caller graph for this function:


The documentation for this class was generated from the following files: