How to allow or deny a user to enter a tab in pagecontrol?

I want to restrict users (based on a special condition) to open a tab or not in the page control. those. the user can click on the tab, but he will not be displayed for him. Instead, the message will show him that " he don't have the access right to see such tab ."

In what event should I write the verification code and what property of the tab ( TPageControl component) will allow / block the user to enter such a tab?

+4
source share
4 answers

In an ideal world, you should set AllowChange to False from the OnChanging event to block the page from being modified. However, this does not seem to be viable because I cannot find a way to find out, from within OnChanging , which page the user is trying to select.

Even looking at the basic Windows notification seems a little hopeful. The TCN_SELCHANGING identifies the control, but says nothing about linked pages, as far as I can tell.

The best I can think of is to use OnChanging to mark the current active page, and then do the hard work in OnChange . If the selected page has been changed to something unwanted, just change it.

 procedure TForm1.PageControl1Changing(Sender: TObject; var AllowChange: Boolean); begin FPreviousPageIndex := PageControl1.ActivePageIndex; end; procedure TForm1.PageControl1Change(Sender: TObject); begin if PageControl1.ActivePageIndex=1 then begin PageControl1.ActivePageIndex := FPreviousPageIndex; Beep; end; end; 

Rather dirty, I know, but it has the power of work!

+7
source

The OnChanging event OnChanging not allow you to determine which tab is selected, since Windows itself does not report this information. However, you can use a subclass of the TPageControl.WindowProc property to intercept messages sent to TPageControl before processing them. Use mouse messages to determine which tab is pressed directly (look at the TPageControl.IndexOfTabAt() method) and use keyboard messages to detect left / right arrow clicks to determine which tab is next to the active tab (look at TPageControl.FindNextPage() method).

+2
source

Use the OnChanging page control event.

 procedure TForm1.PageControl1Changing(Sender: TObject; var AllowChange: Boolean); begin if (self.PageControl1.TabIndex= 1)and (NotAllowUser = 'SomePerson') then begin AllowChange:= False; ShowMessage('Person not allow for this Tab'); end; end; 

Ok, PageControle1.TabIndex is the activepageindex, not the one I want to select. How can I get the page clicked.

 procedure TForm1.PageControl1Changing(Sender: TObject; var AllowChange: Boolean); var P: TPoint; NewTabIndex: Integer; begin P := PageControl1.ScreenToClient(Mouse.CursorPos); NewTabIndex := PageControl1.IndexOfTabAt(PX, Py); if (NewTabIndex= 1) then begin AllowChange:= false; Beep end; end; 

New attempt

  TMyPageControl = Class(TPageControl) private FNewTabSheet: TTabSheet; FOnMyChanging: TMyTabChangingEvent; procedure SetOnMyChanging(const Value: TMyTabChangingEvent); procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY; procedure CMDialogKey(var Message: TCMDialogKey); message CM_DIALOGKEY; protected function CanChange: Boolean; Override; public property OnMyChanging: TMyTabChangingEvent read FOnMyChanging write SetOnMyChanging; End; { TMyPageControl } function TMyPageControl.CanChange: Boolean; begin Result := True; if Assigned(FOnMyChanging) then FOnMyChanging(Self, FNewTabSheet ,Result); end; procedure TMyPageControl.CMDialogKey(var Message: TCMDialogKey); begin if (Focused or Windows.IsChild(Handle, Windows.GetFocus)) and (Message.CharCode = VK_TAB) and (GetKeyState(VK_CONTROL) < 0) then begin FNewTabSheet := FindNextPage(ActivePage, GetKeyState(VK_SHIFT) >= 0,True); SelectNextPage(GetKeyState(VK_SHIFT) >= 0); Message.Result := 1; end else inherited; end; procedure TMyPageControl.CNNotify(var Message: TWMNotify); var P: TPoint; NewTabIndex: Integer; begin with Message do case NMHdr.code of TCN_SELCHANGE: Change; TCN_SELCHANGING: begin Result := 1; P := self.ScreenToClient(Mouse.CursorPos); NewTabIndex := self.IndexOfTabAt(PX, Py); FNewTabSheet:= self.Pages[NewTabIndex]; if CanChange then Result := 0; end; end; end; procedure TMyPageControl.SetOnMyChanging(const Value: TMyTabChangingEvent); begin FOnMyChanging := Value; end; 
+1
source

Sometimes it's better to just hide unwanted TabSheets with something like this:

 TabSheetNN.TabVisible:=Somecondition; 

than trying to prevent the transition to these tabs. Of course, it would be better if Sender in the OnChanging event is TabSheet, and not TPageControl.

0
source

Source: https://habr.com/ru/post/1384672/


All Articles