Rights.cpp 13 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333334335336337338339340341342343344345346347348349350351352353354355356357358359360361362363364365366367368369370371372373374375376377378379380381382383384385386387388389390391392393394395396397398399400401402403404405406407408409410411412413414415416417418419420421422423424425426427428429430431432433434435436437438439440441442443444445446447448449450451452453454455456457458459460461462463464465466467468
  1. //---------------------------------------------------------------------------
  2. #include <vcl.h>
  3. #pragma hdrstop
  4. #include "Rights.h"
  5. #include <Common.h>
  6. #include <VCLCommon.h>
  7. //---------------------------------------------------------------------------
  8. #pragma package(smart_init)
  9. #pragma link "GrayedCheckBox"
  10. #pragma resource "*.dfm"
  11. //---------------------------------------------------------------------------
  12. __fastcall TRightsFrame::TRightsFrame(TComponent* Owner)
  13. : TFrame(Owner)
  14. {
  15. FOnChange = NULL;
  16. FAllowAddXToDirectories = true;
  17. FPopup = false;
  18. FPopupParent = NULL;
  19. FDefaultButton = NULL;
  20. FCancelButton = NULL;
  21. // to avoid duplication of reference in forms that uses the frame
  22. PopupMenu = RightsPopup;
  23. #define COPY_HINT(R) \
  24. Checks[TRights::rrGroup ## R]->Hint = Checks[TRights::rrUser ## R]->Hint; \
  25. Checks[TRights::rrOther ## R]->Hint = Checks[TRights::rrUser ## R]->Hint;
  26. COPY_HINT(Read);
  27. COPY_HINT(Write);
  28. COPY_HINT(Exec);
  29. #undef COPY_HINT
  30. }
  31. //---------------------------------------------------------------------------
  32. __fastcall TRightsFrame::~TRightsFrame()
  33. {
  34. }
  35. //---------------------------------------------------------------------------
  36. void __fastcall TRightsFrame::SetStates(TRights::TRight Right, TRights::TState value)
  37. {
  38. assert(((value == TRights::rsNo) || (value == TRights::rsYes) || (value == TRights::rsUndef)));
  39. TCheckBox * CheckBox = Checks[Right];
  40. if (CheckBox != NULL)
  41. {
  42. switch (value) {
  43. case TRights::rsNo: CheckBox->State = cbUnchecked; break;
  44. case TRights::rsYes: CheckBox->State = cbChecked; break;
  45. case TRights::rsUndef: CheckBox->State = cbGrayed; break;
  46. }
  47. }
  48. }
  49. //---------------------------------------------------------------------------
  50. TRights::TState __fastcall TRightsFrame::GetStates(TRights::TRight Right)
  51. {
  52. TCheckBox * CheckBox = Checks[Right];
  53. if (CheckBox != NULL)
  54. {
  55. switch (CheckBox->State) {
  56. case cbUnchecked: return TRights::rsNo;
  57. case cbChecked: return TRights::rsYes;
  58. case cbGrayed:
  59. default: return TRights::rsUndef;
  60. }
  61. }
  62. else
  63. {
  64. return TRights::rsNo;
  65. }
  66. }
  67. //---------------------------------------------------------------------------
  68. void __fastcall TRightsFrame::SetRights(const TRights & value)
  69. {
  70. AllowUndef = true; // temporarily
  71. for (int Right = TRights::rrFirst; Right <= TRights::rrLast; Right++)
  72. {
  73. States[static_cast<TRights::TRight>(Right)] =
  74. value.RightUndef[static_cast<TRights::TRight>(Right)];
  75. }
  76. AllowUndef = value.AllowUndef;
  77. UpdateControls();
  78. }
  79. //---------------------------------------------------------------------------
  80. TRights __fastcall TRightsFrame::GetRights()
  81. {
  82. TRights Result;
  83. Result.AllowUndef = AllowUndef;
  84. for (int Right = TRights::rrFirst; Right <= TRights::rrLast; Right++)
  85. {
  86. Result.RightUndef[static_cast<TRights::TRight>(Right)] =
  87. States[static_cast<TRights::TRight>(Right)];
  88. }
  89. return Result;
  90. }
  91. //---------------------------------------------------------------------------
  92. void __fastcall TRightsFrame::SetAllowUndef(bool value)
  93. {
  94. for (int Right = TRights::rrFirst; Right <= TRights::rrLast; Right++)
  95. {
  96. TCheckBox * CheckBox = Checks[static_cast<TRights::TRight>(Right)];
  97. if (CheckBox != NULL)
  98. {
  99. CheckBox->AllowGrayed = value;
  100. }
  101. }
  102. }
  103. //---------------------------------------------------------------------------
  104. bool __fastcall TRightsFrame::GetAllowUndef()
  105. {
  106. bool Result = false, First = true;
  107. for (int Right = TRights::rrFirst; Right <= TRights::rrLast; Right++)
  108. {
  109. TCheckBox * Check = Checks[static_cast<TRights::TRight>(Right)];
  110. if (Check != NULL)
  111. {
  112. if (First)
  113. {
  114. Result = Check->AllowGrayed;
  115. First = false;
  116. }
  117. else if (Result != Check->AllowGrayed)
  118. {
  119. assert(false);
  120. }
  121. }
  122. }
  123. return Result;
  124. }
  125. //---------------------------------------------------------------------------
  126. TCheckBox * __fastcall TRightsFrame::GetChecks(TRights::TRight Right)
  127. {
  128. for (int Index = 0; Index < ControlCount; Index++)
  129. {
  130. if (Controls[Index]->InheritsFrom(__classid(TCheckBox)) &&
  131. (Controls[Index]->Tag == TRights::RightToFlag(Right)))
  132. {
  133. return ((TCheckBox *)Controls[Index]);
  134. }
  135. }
  136. return NULL;
  137. }
  138. //---------------------------------------------------------------------------
  139. void __fastcall TRightsFrame::SetAddXToDirectories(bool value)
  140. {
  141. DirectoriesXCheck->Checked = value;
  142. }
  143. //---------------------------------------------------------------------------
  144. bool __fastcall TRightsFrame::GetAddXToDirectories()
  145. {
  146. return DirectoriesXCheck->Checked;
  147. }
  148. //---------------------------------------------------------------------------
  149. void __fastcall TRightsFrame::ControlChange(TObject * /*Sender*/)
  150. {
  151. UpdateControls();
  152. }
  153. //---------------------------------------------------------------------------
  154. void __fastcall TRightsFrame::UpdateControls()
  155. {
  156. Color = (FPopup ? clWindow : clBtnFace);
  157. DirectoriesXCheck->Visible = AllowAddXToDirectories;
  158. EnableControl(DirectoriesXCheck,
  159. Enabled && !((Rights.NumberSet & TRights::rfExec) == TRights::rfExec));
  160. DoChange();
  161. }
  162. //---------------------------------------------------------------------------
  163. void __fastcall TRightsFrame::CycleRights(int Group)
  164. {
  165. TRights::TState State;
  166. bool Same = true;
  167. for (int Right = 0; Right < 3; Right++)
  168. {
  169. TRights::TState CState = States[static_cast<TRights::TRight>(
  170. TRights::rrUserRead + Right + ((Group - 1) * 3))];
  171. if (Right == 0) State = CState;
  172. else
  173. if (State != CState) Same = False;
  174. }
  175. if (!Same)
  176. {
  177. State = TRights::rsYes;
  178. }
  179. else
  180. {
  181. switch (State) {
  182. case TRights::rsYes:
  183. State = TRights::rsNo;
  184. break;
  185. case TRights::rsNo:
  186. State = AllowUndef ? TRights::rsUndef : TRights::rsYes;
  187. break;
  188. case TRights::rsUndef:
  189. State = TRights::rsYes;
  190. break;
  191. }
  192. }
  193. for (int Right = 0; Right < 3; Right++)
  194. {
  195. States[static_cast<TRights::TRight>(
  196. TRights::rrUserRead + Right + ((Group - 1) * 3))] = State;
  197. }
  198. UpdateControls();
  199. }
  200. //---------------------------------------------------------------------------
  201. void __fastcall TRightsFrame::RightsButtonsClick(TObject *Sender)
  202. {
  203. CycleRights(((TComponent*)Sender)->Tag);
  204. }
  205. //---------------------------------------------------------------------------
  206. void __fastcall TRightsFrame::SetAllowAddXToDirectories(bool value)
  207. {
  208. if (FAllowAddXToDirectories != value)
  209. {
  210. FAllowAddXToDirectories = value;
  211. UpdateControls();
  212. }
  213. }
  214. //---------------------------------------------------------------------------
  215. void __fastcall TRightsFrame::DoChange()
  216. {
  217. if (FOnChange)
  218. {
  219. FOnChange(this);
  220. }
  221. }
  222. //---------------------------------------------------------------------------
  223. void __fastcall TRightsFrame::SetEnabled(bool Value)
  224. {
  225. TFrame::SetEnabled(Value);
  226. UpdateControls();
  227. }
  228. //---------------------------------------------------------------------------
  229. void __fastcall TRightsFrame::ForceUpdate()
  230. {
  231. }
  232. //---------------------------------------------------------------------------
  233. void __fastcall TRightsFrame::RightsActionsExecute(TBasicAction * Action,
  234. bool & Handled)
  235. {
  236. TRights R = Rights;
  237. R.Number = TRights::rfNo;
  238. Handled = true;
  239. if (Action == NoRightsAction)
  240. {
  241. R = TRights::rfNo;
  242. }
  243. else if (Action == DefaultRightsAction)
  244. {
  245. R = TRights::rfDefault;
  246. }
  247. else if (Action == AllRightsAction)
  248. {
  249. R = TRights::rfAll;
  250. }
  251. else if (Action == LeaveRightsAsIsAction)
  252. {
  253. R.AllUndef();
  254. }
  255. else
  256. {
  257. Handled = false;
  258. }
  259. Rights = R;
  260. ForceUpdate();
  261. }
  262. //---------------------------------------------------------------------------
  263. void __fastcall TRightsFrame::RightsActionsUpdate(TBasicAction *Action,
  264. bool &Handled)
  265. {
  266. TRights R = Rights;
  267. Handled = true;
  268. if (Action == NoRightsAction)
  269. {
  270. NoRightsAction->Checked = !R.IsUndef && (R.NumberSet == TRights::rfNo);
  271. }
  272. else if (Action == DefaultRightsAction)
  273. {
  274. DefaultRightsAction->Checked = !R.IsUndef && (R.NumberSet == TRights::rfDefault);
  275. }
  276. else if (Action == AllRightsAction)
  277. {
  278. AllRightsAction->Checked = !R.IsUndef && (R.NumberSet == TRights::rfAll);
  279. }
  280. else if (Action == LeaveRightsAsIsAction)
  281. {
  282. LeaveRightsAsIsAction->Enabled = R.AllowUndef;
  283. LeaveRightsAsIsAction->Checked = (R.NumberSet == TRights::rfNo) &&
  284. (R.NumberUnset == TRights::rfNo);
  285. }
  286. else
  287. {
  288. Handled = false;
  289. }
  290. }
  291. //---------------------------------------------------------------------------
  292. void __fastcall TRightsFrame::CreateParams(TCreateParams & Params)
  293. {
  294. TFrame::CreateParams(Params);
  295. if (FPopup)
  296. {
  297. Params.Style |= WS_BORDER;
  298. }
  299. }
  300. //---------------------------------------------------------------------------
  301. void __fastcall TRightsFrame::CreateWnd()
  302. {
  303. if (FPopup)
  304. {
  305. Width += 2 * GetSystemMetrics(SM_CXBORDER);
  306. Height += 2 * GetSystemMetrics(SM_CYBORDER);
  307. }
  308. TFrame::CreateWnd();
  309. }
  310. //---------------------------------------------------------------------------
  311. void __fastcall TRightsFrame::SetPopup(bool value)
  312. {
  313. if (Popup != value)
  314. {
  315. FPopup = value;
  316. Visible = !FPopup;
  317. }
  318. }
  319. //---------------------------------------------------------------------------
  320. void __fastcall TRightsFrame::DoCloseUp()
  321. {
  322. Hide();
  323. if (FDefaultButton != NULL)
  324. {
  325. FDefaultButton->Default = true;
  326. FDefaultButton = NULL;
  327. }
  328. if (FCancelButton != NULL)
  329. {
  330. FCancelButton->Cancel = true;
  331. FCancelButton = NULL;
  332. }
  333. }
  334. //---------------------------------------------------------------------------
  335. void __fastcall TRightsFrame::DoExit()
  336. {
  337. // this is bit hack to make frame hide when ComboEdit button is pressed while
  338. // from is poped-up already.
  339. if (FPopup && !IsAncestor(Screen->ActiveControl, FPopupParent))
  340. {
  341. DoCloseUp();
  342. }
  343. TFrame::DoExit();
  344. }
  345. //---------------------------------------------------------------------------
  346. bool __fastcall TRightsFrame::IsAncestor(TControl * Control, TControl * Ancestor)
  347. {
  348. while ((Control != NULL) &&
  349. (Control->Parent != Ancestor))
  350. {
  351. Control = Control->Parent;
  352. }
  353. return (Control != NULL);
  354. }
  355. //---------------------------------------------------------------------------
  356. void __fastcall TRightsFrame::CMDialogKey(TCMDialogKey & Message)
  357. {
  358. if (FPopup && Visible &&
  359. ((Message.CharCode == VK_RETURN) ||
  360. (Message.CharCode == VK_ESCAPE)) &&
  361. KeyDataToShiftState(Message.KeyData).Empty())
  362. {
  363. CloseUp();
  364. Message.Result = 1;
  365. }
  366. else
  367. {
  368. TFrame::Dispatch(&Message);
  369. }
  370. }
  371. //---------------------------------------------------------------------------
  372. void __fastcall TRightsFrame::CMCancelMode(TCMCancelMode & Message)
  373. {
  374. if (FPopup && Visible &&
  375. ((Message.Sender == NULL) ||
  376. (!IsAncestor(Message.Sender, this) &&
  377. !IsAncestor(Message.Sender, FPopupParent) &&
  378. (Message.Sender != this))))
  379. {
  380. CloseUp();
  381. }
  382. TFrame::Dispatch(&Message);
  383. }
  384. //---------------------------------------------------------------------------
  385. void __fastcall TRightsFrame::Dispatch(void * Message)
  386. {
  387. TMessage & AMessage = *static_cast<TMessage *>(Message);
  388. switch (AMessage.Msg)
  389. {
  390. case CM_CANCELMODE:
  391. CMCancelMode(*(TCMCancelMode *)Message);
  392. break;
  393. case CM_DIALOGKEY:
  394. CMDialogKey(*(TCMDialogKey *)Message);
  395. break;
  396. default:
  397. TFrame::Dispatch(Message);
  398. break;
  399. }
  400. }
  401. //---------------------------------------------------------------------------
  402. void __fastcall TRightsFrame::DropDown()
  403. {
  404. TCustomForm * Form = GetParentForm(this);
  405. // due to lack of better idea, we clear "default" and "cancel" flags of respective
  406. // form buttons to prevent them to handle ESC/ENTER keys.
  407. for (int Index = 0; Index < Form->ControlCount; Index++)
  408. {
  409. TButton * Button = dynamic_cast<TButton *>(Form->Controls[Index]);
  410. if (Button != NULL)
  411. {
  412. if (Button->Default)
  413. {
  414. assert(FDefaultButton == NULL);
  415. FDefaultButton = Button;
  416. Button->Default = false;
  417. }
  418. if (Button->Cancel)
  419. {
  420. assert(FCancelButton == NULL);
  421. FCancelButton = Button;
  422. Button->Cancel = false;
  423. }
  424. }
  425. }
  426. TPoint Origin(PopupParent->Left, PopupParent->Top + PopupParent->Height);
  427. Origin = Parent->ScreenToClient(PopupParent->Parent->ClientToScreen(Origin));
  428. if (Origin.x + Width > Parent->ClientWidth)
  429. {
  430. Origin.x += PopupParent->Width - Width;
  431. }
  432. Left = Origin.x;
  433. Top = Origin.y;
  434. Show();
  435. SetFocus();
  436. }
  437. //---------------------------------------------------------------------------
  438. void __fastcall TRightsFrame::CloseUp()
  439. {
  440. assert(FPopup);
  441. assert(Visible);
  442. if (!Focused())
  443. {
  444. // this can happen only if called from on-click handler of drop down button
  445. DoCloseUp();
  446. }
  447. FPopupParent->SetFocus();
  448. }
  449. //---------------------------------------------------------------------------