CollectionViewUtils.cpp 6.1 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227
  1. // Copyright 2017-2021 marynate. All Rights Reserved.
  2. #include "CollectionViewUtils.h"
  3. #include "Misc/Paths.h"
  4. #include "Misc/ConfigCacheIni.h"
  5. #include "ICollectionManager.h"
  6. #include "CollectionManagerModule.h"
  7. #define LOCTEXT_NAMESPACE "CollectionView"
  8. namespace CollectionViewUtils
  9. {
  10. /** Create a string of the form "CollectionName:CollectionType */
  11. FString ToConfigKey(const FString& InCollectionName, const ECollectionShareType::Type& InCollectionType)
  12. {
  13. static_assert(ECollectionShareType::CST_All == 4, "Update CollectionViewUtils::ToConfigKey for the updated ECollectionShareType values");
  14. check(InCollectionType != ECollectionShareType::CST_All);
  15. FString CollectionTypeStr;
  16. switch(InCollectionType)
  17. {
  18. case ECollectionShareType::CST_System:
  19. CollectionTypeStr = "System";
  20. break;
  21. case ECollectionShareType::CST_Local:
  22. CollectionTypeStr = "Local";
  23. break;
  24. case ECollectionShareType::CST_Private:
  25. CollectionTypeStr = "Private";
  26. break;
  27. case ECollectionShareType::CST_Shared:
  28. CollectionTypeStr = "Shared";
  29. break;
  30. default:
  31. break;
  32. }
  33. return InCollectionName + ":" + CollectionTypeStr;
  34. }
  35. /** Convert a string of the form "CollectionName:CollectionType back into its individual elements */
  36. bool FromConfigKey(const FString& InKey, FString& OutCollectionName, ECollectionShareType::Type& OutCollectionType)
  37. {
  38. static_assert(ECollectionShareType::CST_All == 4, "Update CollectionViewUtils::FromConfigKey for the updated ECollectionShareType values");
  39. FString CollectionTypeStr;
  40. if(InKey.Split(":", &OutCollectionName, &CollectionTypeStr, ESearchCase::IgnoreCase, ESearchDir::FromEnd))
  41. {
  42. if(CollectionTypeStr == "System")
  43. {
  44. OutCollectionType = ECollectionShareType::CST_System;
  45. }
  46. else if(CollectionTypeStr == "Local")
  47. {
  48. OutCollectionType = ECollectionShareType::CST_Local;
  49. }
  50. else if(CollectionTypeStr == "Private")
  51. {
  52. OutCollectionType = ECollectionShareType::CST_Private;
  53. }
  54. else if(CollectionTypeStr == "Shared")
  55. {
  56. OutCollectionType = ECollectionShareType::CST_Shared;
  57. }
  58. else
  59. {
  60. return false;
  61. }
  62. return !OutCollectionName.IsEmpty();
  63. }
  64. return false;
  65. }
  66. // Keep a map of all the collections that have custom colors, so updating the color in one location updates them all
  67. static TMap<FString, TSharedPtr<FLinearColor>> CollectionColors;
  68. }
  69. const TSharedPtr<FLinearColor> CollectionViewUtils::LoadColor(const FString& InCollectionName, const ECollectionShareType::Type& InCollectionType)
  70. {
  71. check(InCollectionType != ECollectionShareType::CST_All);
  72. const FString ColorKeyStr = ToConfigKey(InCollectionName, InCollectionType);
  73. // See if we have a value cached first
  74. {
  75. TSharedPtr<FLinearColor>* const CachedColor = CollectionColors.Find(ColorKeyStr);
  76. if(CachedColor)
  77. {
  78. return *CachedColor;
  79. }
  80. }
  81. // Loads the color of collection at the given path from the config
  82. if(FPaths::FileExists(GEditorPerProjectIni))
  83. {
  84. // Create a new entry from the config, skip if it's default
  85. FString ColorStr;
  86. if(GConfig->GetString(TEXT("CollectionColor"), *ColorKeyStr, ColorStr, GEditorPerProjectIni))
  87. {
  88. FLinearColor Color;
  89. if(Color.InitFromString(ColorStr) && !Color.Equals(CollectionViewUtils::GetDefaultColor()))
  90. {
  91. return CollectionColors.Add(ColorKeyStr, MakeShareable(new FLinearColor(Color)));
  92. }
  93. }
  94. else
  95. {
  96. return CollectionColors.Add(ColorKeyStr, MakeShareable(new FLinearColor(CollectionViewUtils::GetDefaultColor())));
  97. }
  98. }
  99. return nullptr;
  100. }
  101. void CollectionViewUtils::SaveColor(const FString& InCollectionName, const ECollectionShareType::Type& InCollectionType, const TSharedPtr<FLinearColor> CollectionColor, const bool bForceAdd)
  102. {
  103. check(InCollectionType != ECollectionShareType::CST_All);
  104. const FString ColorKeyStr = ToConfigKey(InCollectionName, InCollectionType);
  105. // Remove the color if it's invalid or default
  106. const bool bRemove = !CollectionColor.IsValid() || (!bForceAdd && CollectionColor->Equals(CollectionViewUtils::GetDefaultColor()));
  107. // Saves the color of the collection to the config
  108. if(FPaths::FileExists(GEditorPerProjectIni))
  109. {
  110. // If this is no longer custom, remove it
  111. if(bRemove)
  112. {
  113. GConfig->RemoveKey(TEXT("CollectionColor"), *ColorKeyStr, GEditorPerProjectIni);
  114. }
  115. else
  116. {
  117. GConfig->SetString(TEXT("CollectionColor"), *ColorKeyStr, *CollectionColor->ToString(), GEditorPerProjectIni);
  118. }
  119. }
  120. // Update the map too
  121. if(bRemove)
  122. {
  123. CollectionColors.Remove(ColorKeyStr);
  124. }
  125. else
  126. {
  127. CollectionColors.Add(ColorKeyStr, CollectionColor);
  128. }
  129. }
  130. bool CollectionViewUtils::HasCustomColors( TArray< FLinearColor >* OutColors )
  131. {
  132. if(!FPaths::FileExists(GEditorPerProjectIni))
  133. {
  134. return false;
  135. }
  136. // Read individual entries from a config file.
  137. TArray<FString> Section;
  138. GConfig->GetSection(TEXT("CollectionColor"), Section, GEditorPerProjectIni);
  139. bool bHasCustom = false;
  140. const FCollectionManagerModule& CollectionManagerModule = FCollectionManagerModule::GetModule();
  141. const ICollectionManager& CollectionManager = CollectionManagerModule.Get();
  142. for(FString& EntryStr : Section)
  143. {
  144. EntryStr.TrimStartInline();
  145. FString ColorKeyStr;
  146. FString ColorStr;
  147. if(!EntryStr.Split("=", &ColorKeyStr, &ColorStr))
  148. {
  149. continue;
  150. }
  151. // Ignore any that have invalid or default colors
  152. FLinearColor CurrentColor;
  153. if(!CurrentColor.InitFromString(ColorStr) || CurrentColor.Equals(CollectionViewUtils::GetDefaultColor()))
  154. {
  155. continue;
  156. }
  157. // Ignore any that reference old collections
  158. FString CollectionName;
  159. ECollectionShareType::Type CollectionType;
  160. if(!FromConfigKey(ColorKeyStr, CollectionName, CollectionType) || !CollectionManager.CollectionExists(*CollectionName, CollectionType))
  161. {
  162. continue;
  163. }
  164. bHasCustom = true;
  165. if(OutColors)
  166. {
  167. // Only add if not already present (ignores near matches too)
  168. bool bAdded = false;
  169. for(const FLinearColor& Color : *OutColors)
  170. {
  171. if(CurrentColor.Equals(Color))
  172. {
  173. bAdded = true;
  174. break;
  175. }
  176. }
  177. if(!bAdded)
  178. {
  179. OutColors->Add(CurrentColor);
  180. }
  181. }
  182. else
  183. {
  184. break;
  185. }
  186. }
  187. return bHasCustom;
  188. }
  189. FLinearColor CollectionViewUtils::GetDefaultColor()
  190. {
  191. // The default tint the folder should appear as
  192. return FLinearColor::Gray;
  193. }
  194. #undef LOCTEXT_NAMESPACE