Prevent Cut functionality within Unbound Combobox (1 Viewer)

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
I am trying to prevent any foolish behavior from taking place upon a form. I have textboxes and comboboxes that users need to input data into or make selections within.

I came up with a method to prevent Paste as follows:

Code:
Private Sub ComboBox_KeyDown(KeyCode As Integer, Shift As Integer)
    Call PurgeClipBoard()
End Sub

Public Sub PurgeClipBoard()
    If apiOpenClipboard(0&) <> 0 Then
       Call apiEmptyClipboard()
       Call apiCloseClipboard()
    End If
End Sub

Now while this does not actually prevent pasting it does prevent anything from being pasted which functionally is sufficient. Further I do not need to prevent them from performing a Copy but if there is a more elegant way to do this and affect all 3 functionalities that would be fantastic

Note I want to prevent both {Ctrl}-X as well as the Right-Click-Mouse-Cut Event

I have tried doing it within the Keydown event but that does not prevent keyboard Cut/Copy/Paste because the initial Keydown for {Ctrl} cannot be disabled if it is held down and then the subsequent Keydown for X, C, or V is not prevented and I cannot debug it to see what is taking place due to Focus issues. The following is what I had in my Keydown event to try and prevent Cut/Paste but it does not work.

Code:
Private Sub ComboBox_KeyDown(KeyCode As Integer, Shift As Integer)
    If Shift = acCtrlMask And (Keycode = vbKeyX or Keycode = vbKeyV) Then
        Shift = 0
        KeyCode = vbNull
    End If
End Sub

Note: The above kind of works if I do the following as a form of debugging:

Code:
Private Sub ComboBox_KeyDown(KeyCode As Integer, Shift As Integer)
    Call PurgeClipBoard()
    If Shift = acCtrlMask Then
        If KeyCode = vbKeyC Then
            Call MsgBox("Copy Text")
        ElseIf KeyCode = vbKeyV Then
            Call MsgBox("Paste Text")
        ElseIf KeyCode = vbKeyX Then
            Call MsgBox("Cut Text")
        End If
    End If
    If KeyCode <> 9 Then    'Allow Tab
        KeyCode = vbNull
    End If
End Sub

However if I remove the MsgBox logic then the Cut is not prevented.

Any help on this issue would be greatly appreciated and/or I hope what I have presented might help someone else at least with preventing pasting. Note you need to include the Declares for those api functions if you use them.
 

spikepl

Eledittingent Beliped
Local time
Today, 23:18
Joined
Nov 3, 2010
Messages
6,142
It is not clear what you mean by

foolish behavior

Also, what is the purpose of preventing cut/copy/paste?You allow normal typing but not paste? What does this prevent?
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
By foolish behavior I mean: Anything and everything that a user could do that is not what the software was meant to be used for. Basically this sequenced into the concept of trying to make the software foolproof (yeah I know if I build foolproof software they will just build a better fool). Still the biggest issue in this case is inputting bad data or doing something that causes the software to error out.

I have run into the issue of Cut/Copy/Paste before in other software languages and dealt with it but I have not tried to circumnavigate the issues created by Cut/Copy/Paste within Access as of yet.

If Cut/Copy/Paste are not needed and/or not wanted in the software interface then it is best to disable them as this can cause unexpected results that either allow bad data to get in or cause the program to error out.

As stated Copy for this situation I do not really care about and Paste I have already found a way to disable it. The only one that I am having troubles with is the Cut. I cannot seem to stop someone from cutting the contents of the Combobox and thus causing an error.
 

MarkK

bit cruncher
Local time
Today, 14:18
Joined
Mar 17, 2004
Messages
8,186
I think cut/copy/paste are really useful functions. I would rather just validate the data during or after entry, and reject data that doesn't conform, rather than try to control how the user enters said data.
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Great and if that were the case for this situation I would do just that :) however that is not the case for this situation.

Note: I am a senior software engineer and I have doing this kind of stuff for over 25+ years I know what this UI needs to do and does not need to do. I am just striving to see if anyone has a solution that allows me to disable the Cut ability.
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
Can you set a variable as a flag on the Ctrl press then test it when the next key is pressed?
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Okay I am not understanding the why of your question -- are you saying put some dummy process into the code in order to try and get the Cut not too function -- or -- are you saying that I should check this variable for some reason?

But to answer your question yes I could do this but I am not sure why you are asking? Could you please explain?
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
You need to test for the condition of the ctrl key before you process the X key.

Rough code concept demo:

Code:
Dim ctrlflag As Boolean

Private Sub Combo0_KeyDown(KeyCode As Integer, Shift As Integer)

      If KeyCode = vbKeyControl Then
        ctrlflag = True
    ElseIf ctrlflag And KeyCode = vbKeyX Then
        Debug.Print "Don't do it"
    Else
        Debug.Print "Do it"
    End If
        
End Sub
 
Private Sub Combo0_KeyUp(KeyCode As Integer, Shift As Integer)
 
     If KeyCode = vbKeyControl Then ctrlflag = False

 End Sub
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Okay yes I did something similar to this but that did not stop the Cut from taking place. The only thing I have done so for that causes the Cut to not happen is put a MsgBox call in denoting what is happening

What I did within the KeyDown event is:

Code:
[FONT="Courier New"]Dim mPrevKeyCode As Integer  (m indicates module scope variable)
....
    Call PurgeClipBoard( )   ' This sub prevents Paste
    If mPrevKeyCode = vbKeyControl And Shift = 2 Then
        KeyCode = vbNull
    Else
        mPrevKeyCode = KeyCode
        Select Case KeyCode
            Case vbKeyTab, vbKeyUp, vbKeyDown, vbKeyEscape
                Okay = 1  'Aka do nothing
            Case Else
                KeyCode = vbNull
        End Select
    End If[/FONT]

What did work

Code:
[FONT="Courier New"]    Call PurgeClipBoard( )   ' This sub prevents Paste
    If Shift = 2 Then
        If KeyCode = vbKeyX
            Call MsgBox ("Attempting to Cut")
            KeyCode = vbNull
            Shift = 0
        End If
    End If[/FONT]

Originally I just had the following:

Code:
[FONT="Courier New"]        Select Case KeyCode
            Case vbKeyTab, vbKeyUp, vbKeyDown, vbKeyEscape
                Okay = 1  'Aka do nothing
            Case Else
                KeyCode = vbNull
        End Select
[/FONT]

It is a Combobox and I do not want them keying anything that is not relevant to what this Combobox is meant for and this seemed like the most concise method to do that however it does not stop Paste nor Cut and presumably not Copy either although I have not tested that
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
I don't have the time to look closely just now. However I can see you are misusing vbNull. Don't know if it is the source of the actual problem though.

vbNull is not a Null per se but the constant for a datatype and has the value of 1.

See post 15 in this thread for a more detailed explanation.
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
*Sigh* got to love Microsoft for the technical obscurity ... Not

Okay so vbNull = 1 not Null got it but that should still negate the Cut request since vbNull <> vbKeyX and I have also tried setting Shift = 0 in conjunction but that had no affect either.

So far the only thing that seems to work is to cause the ComboBox to lose focus and then regain Focus -- aka pop a MsgBox -- but I definitely do not want to do that -- or maybe I do *sigh*

I have always marveled at the counter-intuitiveness of Microsoft products.

So far -- I have found no answer to how to elegantly disable the Cut functionality which is my original question and I am sure other Access developers have run into this issue ... the big question is has anyone heard how to resolve it?
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
Okay yes I did something similar to this but that did not stop the Cut from taking place.

You might think your code is similar but clearly it isn't because you would see the code I posted works fine if you actually tried it.

You are barking up the wrong tree trying to clear the clipboard. Stop the action at its source by simply catching the X, C or V when the ctrl key is down.

Here is the complete code. Do try it.

Code:
Dim ctrlflag As Boolean
  
Private Sub Combo0_KeyDown(KeyCode As Integer, Shift As Integer)
 
    If KeyCode = vbKeyControl Then
        ctrlflag = True
    ElseIf ctrlflag And (KeyCode = vbKeyX Or KeyCode = vbKeyC Or KeyCode = vbKeyV) Then KeyCode = 0
    End If
        
End Sub
  
Private Sub Combo0_KeyUp(KeyCode As Integer, Shift As Integer)
  
     If KeyCode = vbKeyControl Then ctrlflag = False
  
 End Sub
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Okay I am utterly amazed -- It works! -- Okay can you explain to me why that works but the following does not?

Code:
[FONT="Courier New"]
If Shift = acCtrlMask Then
    If KeyCode = vbKeyX Or KeyCode = vbKeyC Or KeyCode = vbKeyV Then
        Shift = 0
        KeyCode = 0
    End If
End If
[/FONT]
If I put a debug stop in the code inside the second If on the "Shift = 0" I can see that it gets here when I do any of these functions and it works to do what it supposed to do if I press F5. HOWEVER, if I do not put a break in then it does not do what it is supposed to do.

I even turned on the Form.[Key Preview] property and put the above in the KeyDown event of the Form and again I can verify that it gets inside the inner If with a break point and works but without the break point it does not work?

I mean I can also accept that you simply do not know as there are many things about Microsoft's software that make absolutely no sense and one just has to accept that it is what it is and that is how you get it to do what you want it to do.
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
Okay I am utterly amazed -- It works! -- Okay can you explain to me why that works but the following does not/

The mystery deepens. :confused: The code you posted does work for me.

I have never needed to use the Shift argument in KeyDown before so I had never looked into how it is meant to be used. I came up with my code due to my ignorance of the proper method which it appears you have used.
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Okay I am done :) -- What you gave me works -- I have discontinued beating my head on the proverbial wall that is Microsoft -- I am content with the work around -- if you are not then by all means enjoy delving into the mystery if you do come up with a why then let me know. BTW I used your answer and applied it to the Form after setting the Form.[KeyPreview] = Yes and low and behold it works there as well. While my version does not work for me in either place.

Oh and might I remind you that mine did work for me if I either did a debug stop within the inner If statement or put a MsgBox within the inner If statement but without one or the other it does not work for me.
 

Galaxiom

Super Moderator
Staff member
Local time
Tomorrow, 07:18
Joined
Jan 20, 2009
Messages
12,854
Odd that the break point "cures" it. Maybe it is a timing issue.

Maybe try your database on another PC and see if it misbehaves there too.

If it does I would try a decompile. (Backup first as decompile is undocumented and potentially dangerous.)

If it is only on your computer I would try a repair Office installation.

BTW My test was with A2010 on Windows 7.
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
Hmm Windows 7 with A2013 :) maybe its a new undocumented enhancement :)
 

vbaInet

AWF VIP
Local time
Today, 22:18
Joined
Jan 22, 2010
Messages
26,374
Okay I am utterly amazed -- It works! -- Okay can you explain to me why that works but the following does not?
Perhaps your PC is too powerful in that the cut wants to happen quicker than the VBA validation ;)

Try breaking it down:
Code:
    If Shift = Access.acCtrlMask Then
        If KeyCode = vbKeyX Then
            KeyCode = 0
        ElseIf KeyCode = vbKeyC Then
            KeyCode = 0
        ElseIf KeyCode = vbKeyV Then
            KeyCode = 0
        End If
    End If
... and apologies for posting in an old thread. :)
 

DennisOJensen

Registered User.
Local time
Today, 17:18
Joined
Jun 28, 2015
Messages
62
First no apology needed -- input is always welcome. I doubt its speed the unit I have is not a powerhouse in fact it is barely a development machine -- prior to getting a memory upgrade the thing only had 4MB of Ram no it has a whomping 8MB.

Still I have worked with a lot of event handling situations but this is the first that I have encountered where the "proper" means of implementation did not work. Further I think I tried what you suggested and that did not work either but again thanks.
 

vbaInet

AWF VIP
Local time
Today, 22:18
Joined
Jan 22, 2010
Messages
26,374
First no apology needed -- input is always welcome. I doubt its speed the unit I have is not a powerhouse in fact it is barely a development machine -- prior to getting a memory upgrade the thing only had 4MB of Ram no it has a whomping 8MB.
I only said that in jest, hence the wink ;).

Strange occurence. I would hope that DoEvents would cure the problem but it's not an ideal piece of code for this scenario.
 

Users who are viewing this thread

Top Bottom