none
Outlook - Prevent a user from editing an Appointment "Subject" RRS feed

  • Question

  • A VSTO Outlook Add-In with an Adjoining Form Region

    How to prevent a user from editing the Outlook Appointment Subject? 

    Friday, December 16, 2016 11:55 AM

All replies

  • Hello Andrew,

    There is no trivial way for preventing users from changing the subject line.

    You may consider changing the layout of your form region to the replace-all one which replaces the whole Outlook form with the form region. See Creating Outlook Form Regions for more information.


    profile for Eugene Astafiev at Stack Overflow, Q&A for professional and enthusiast programmers

    Friday, December 16, 2016 4:09 PM
  • Thanks 

    A ReplaceAll Form Region disables most of the Outlook ribbon, so is not an option for this add-in

    Is there a non-trivial way??

    Friday, December 16, 2016 4:29 PM
  • Hi Andrew,

    You can create a custom form and publish it for users. 

    Or may consider using the ReplaceAll form region and rebuilding the ribbon UI from scratch specifying idMso values. You can find built-in control IDs in the following documents:

    Office 2010 Help Files: Office Fluent User Interface Control Identifiers

    Office 2013 Help Files: Office Fluent User Interface Control Identifiers

    Office 2016 Help Files: Office Fluent User Interface Control Identifiers


    profile for Eugene Astafiev at Stack Overflow, Q&A for professional and enthusiast programmers

    Sunday, December 18, 2016 5:42 PM
  • "you can create a custom form and publish it for users"

    This is an addin we sell - it needs to be independent of creating forms within Otulook

    "Or may consider using the ReplaceAll form region"

    See my previous post 

    "rebuilding the ribbon UI from scratch"

    This would be A HUGE HUGE task - possibly not even possible

    Monday, December 19, 2016 7:51 AM
  • Andrew,

    There is no other way. 


    profile for Eugene Astafiev at Stack Overflow, Q&A for professional and enthusiast programmers

    Monday, December 19, 2016 3:15 PM
  • "There are always options"

    Captain Jean-Luc Picard

    Tuesday, December 20, 2016 8:17 AM
  • Hi,

    We could handle AppointmentItem.PropertyChange Event (Outlook) to prevent users editing the subject.

         public string oriName;
            private void ThisAddIn_Startup(object sender, System.EventArgs e)
            {
                Application.Inspectors.NewInspector += Inspectors_NewInspector;
            }
      private void Inspectors_NewInspector(Outlook.Inspector Inspector)
            {
                  Object item = Inspector.CurrentItem;
                if (item is Outlook.AppointmentItem)
                {
                    Outlook.AppointmentItem apptItem = item as Outlook.AppointmentItem;
                    oriName = apptItem.Subject;
                    if (oriName != null)
                    {
                        apptItem.PropertyChange += appItem_PropertyChange;
                    }
                }
            }
    
            private void appItem_PropertyChange(string Name)
            {
                if (Name == "Subject")
                {
                    Outlook.Inspector insp = Application.ActiveInspector();
                    Object item = insp.CurrentItem;
                    MessageBox.Show("You could not change it");
                    if (item is Outlook.AppointmentItem)
                    {
                        Outlook.AppointmentItem appItem = item as Outlook.AppointmentItem;
                        appItem.Subject = oriName;
                    }
                }
            }
    

    Regards,

    Celeste


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Thursday, December 29, 2016 8:54 AM
    Moderator
  • Thanks Celeste

    I was already doing this in my VSTO Form Region

    However : 

    * It does not PREVENT a user editing the Subject 

    * It just restores the original Subject text

    Saturday, December 31, 2016 3:33 PM
  • Hi,

    If you want to set it into read-only, I think it is impossible. It is a workaround to handle PropertyChange event resetting the Subject.

    Regards,

    Celeste


    MSDN Community Support
    Please remember to click "Mark as Answer" the responses that resolved your issue, and to click "Unmark as Answer" if not. This can be beneficial to other community members reading this thread. If you have any compliments or complaints to MSDN Support, feel free to contact MSDNFSF@microsoft.com.

    Tuesday, January 3, 2017 2:27 AM
    Moderator
  • Andrew,

    As I wrote previously, there is no way trivial way for preventing the subject line from editing. The only possible way is to use a form region.


    profile for Eugene Astafiev at Stack Overflow, Q&A for professional and enthusiast programmers

    Tuesday, January 3, 2017 6:39 PM
  • Hi Andrew,

    Microsoft did not think of this when building their object models so you will have to build it yourself.

    First you will need to get the Handle to the Inspector Window that opens when you click on a appointment.  You can do this how you wish.

    You can then callMakeSubjectReadonly.  You need to give it the hWnd to the Inspector window AND so that it finds the right subject you need to tell it the item type. In your case if you just want this for appointments then olAppointment.

    As Always please understand that this finds the Subject window by going down through the window class names.  You need to test it on each version of Outlook.  I am pretty sure this will work on 2007 / 2010 but I do not have any others so have not tested it.

    Hope this helps.

    I would also now suggest this bee the answer to your question.

            <DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _
            Public Shared Function GetDlgItem(ByVal hDlg As IntPtr, ByVal nIDDlgItem As IntPtr) As IntPtr
            End Function

    <DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _ Private Shared Function SendMessage(ByVal hWnd As IntPtr, ByVal Msg As UInteger, ByVal wParam As IntPtr, ByVal lParam As IntPtr) As IntPtr End Function <DllImport("user32.dll", SetLastError:=True, CharSet:=CharSet.Auto)> _ Public Shared Function FindWindowEx(ByVal parentHandle As IntPtr, _ ByVal childAfter As IntPtr, _ ByVal lclassName As String, _ ByVal windowTitle As String) As IntPtr End Function ''' <summary> ''' The ID of the edit control ''' </summary> Private Const ID_Subject_Mail = &H1005 ''' <summary> ''' The ID of the edit control ''' </summary> Private Const ID_Subject_Tasks = &H1001 ''' <summary> ''' The ID of the edit control ''' </summary> Private Const ID_Subject_Appointment = &H1004 Private EM_SETREADONLY As IntPtr = &HCF Public sub MakeSubjectReadonly(ByVal inspectorHwnd As IntPtr, ByVal selClassType As Outlook.OlObjectClass) Dim subjectHwnd As IntPtr = GetSubjectWindow(inspectorHwnd, selClassType) SendMessage(subjectHwnd, EM_SETREADONLY, 1, 0) End Sub Private Function GetSubjectWindow(ByVal aHwnd As IntPtr, ByVal selClassType As Outlook.OlObjectClass) As IntPtr Dim hwnd1 As IntPtr = IntPtr.Zero Dim hwnd2 As IntPtr = IntPtr.Zero Dim hwnd3 As IntPtr = IntPtr.Zero Dim hwnd4 As IntPtr = IntPtr.Zero Dim hwnd5 As IntPtr = IntPtr.Zero Try hwnd2 = FindWindowEx(aHwnd, IntPtr.Zero, "AfxWndW", vbNullString) hwnd3 = FindWindowEx(hwnd2, IntPtr.Zero, "AfxWndW", vbNullString) hwnd4 = FindWindowEx(hwnd3, IntPtr.Zero, "#32770", vbNullString) Select Case selClassType Case Outlook.OlObjectClass.olMail hwnd5 = GetDlgItem(hwnd4, ID_Subject_Mail) Case Outlook.OlObjectClass.olAppointment, Outlook.OlObjectClass.olMeetingRequest hwnd5 = GetDlgItem(hwnd4, ID_Subject_Appointment) Case Outlook.OlObjectClass.olTask hwnd5 = GetDlgItem(hwnd4, ID_Subject_Tasks) Case Else End Select Return hwnd5 Catch ex As Exception End Try Return IntPtr.Zero End Function



    • Proposed as answer by donky73 Thursday, January 5, 2017 7:01 AM
    • Edited by donky73 Friday, January 6, 2017 5:52 AM
    Thursday, January 5, 2017 7:00 AM
  • Thanks

    That it an interesting approach!

    I will create a test solution using this approach and report back on here what happens

    Thursday, January 5, 2017 9:35 AM
  • Sorry I forgot to add the GetDlgItem signature and the NativeMethodsEX parts.

    By the way you should wait until the Inspector is Activated before getting the Hwnd.

    Friday, January 6, 2017 5:54 AM
  • I converted your VB.Net code to C# 

    My code gets Window Handles successfully except here

     hwnd5 = GetDlgItem(hwnd4, ID_Subject_Appointment);

    which always sets hwnd5 to zero.

    ID_Subject_Appointment has IntPtr value 1004

    (1004 is decimal equivalent of hex 1004)


    Friday, January 6, 2017 4:09 PM
  • Sorry I did not realise you are doing it in C#.  I always have issues with these messages and converting them from C# to VB.net.

    In C# it would be 0x1005 as far as I know.

    If you still have problems then let us start at the beginning.

    1. What Outlook Version do you have?
    2. Outlook Item type of the Inspector window is olAppointment?
    3. hwnd4 produces a result?
    4. Check with SPY ++ or get Winspector
    5. My Spy++ says the subject window has a Control ID: 00001004

    Let me know how you go.

    Sunday, January 8, 2017 9:11 AM
  • Outlook 2013

    Yes - an Appointment Item

    hwnd 4 produces a result

    I am using ControlId 00001004

    Sunday, January 8, 2017 10:14 AM
  • Do you have spy ++ (comes with VS) or winspector spy free to download.  It slows everything down but works ok?

    I dont have Office 2013 to test.

    Sunday, January 8, 2017 11:13 AM
  • I don't 

    I do have spy++ which comes with .Net 

    Sunday, January 8, 2017 11:29 AM
  • Looks like you will have to fire up your Spy ++ and check what you have.  Set Spy++ onto the subject text box.  Here is my pic.  I have marked with red the windows my code finds.  Does 2013 match this?

    Sunday, January 8, 2017 11:41 AM