VBA Replacement for Flag Status - vba

According to documentation, the MailItem.FlagStatus property in Outlook is deprecated. So what does Outlook use to mark a mail item as "in progress" or "waiting on someone else" when said item is flagged and thus appears in the to-do list? I'd like to programatically change the status of items in the to do list, but only Task Items have the Status property and I can't figure out the correct equivalent for mail items.
While Programmatically setting a MailItem's followup flag to complete? is related, I don't believe it answers my question. The Flag Request property appears to document the associated follow up action, rather than assigning one of the standard statuses used for Task Items (Not Started, In Progress, Waiting on Someone Else, Deferred, Completed).
What I'm trying to do is this: outlook's to-do view allows you to set the Status of both task items and flagged mail items.
You can also set the status of task items programmatically by assigning to the Status property, e.g. myTaskItem.Status = olTaskWaiting sets the status to "Waiting on Someone Else". I'm trying to figure out how to do the same thing to mail items. I have attempted to do this via myMailItem.FlagStatusand been unsuccessful: while Flag Status does correspond to some of the statuses, it does not do so uniquely (0 seems to equal both In Progress and Deferred). Since Flag Status is deprecated anyway, I thought there might be some other way to set these values.
My Progress:
This page has someone with nearly exactly the same question I do, and the answer seems to suggest that the "status" property is added directly to the mail item when it is flagged as a to-do. However, I'm not sure under what name task status has been added. Item.Status gives me the error "Object doesn't support this property or method", and Item.UserProperties("Status") also gives an error.

My take on this is that because FlagIcon and FlagStatus are deprecated (and probably have been since OL2007), everyone needs to rethink their objectives and revise their VBA code. At some point, Outlook will stop putting values in those properties (or the properties will go away and throw an error).
My code was looking for instances in which a mail item had a follow-up flag but no reminder. My rule was that mail requiring follow-up should have a reminder. In the new system, it looks like mail follow-up is similar to task follow-up, so looking at the mail item as a task, my code now looks for mail items that have a start or due date and are not completed but have no reminder set, as in the following:
If (myMail.TaskStartDate <> #1/1/4501# _
Or _
myMail.TaskDueDate <> #1/1/4501#) _
And myMail.TaskCompletedDate = #1/1/4501# _
And Not myMail.ReminderSet Then
'Do something here ...
End If
This is a lot more complex than before, but what can you do in the face of progress? :-D
(P.S. If there is a better way to code for "no date" than "#1/1/4501#" please let me know.)

Related

Outlook Instant Search - hit and miss results

I have the below code to run an instant search from a tool I've developed that iterates through all Outlook folders and then uses the restrict method to get two counts, first the total and the second, a count of those items that are two years or older.
Once done, this is displayed to the user in a listview and the code below is supposed to do an instant search query on the selected result using the 'received' date to limit the results.
What I've found is that sometimes the instant result filters the results and in other cases it purely displays all items from within the selected folder. For example, a folder has 90 items but 5 are over 2 years old, sometimes it will show 5 (generally after the selection has been made from the listview twice) and the rest of the time the full 90 are shown.
Has anyone else come across this is and managed to resolve it?
Private Sub OpenOlFolder(sender As Object, e As EventArgs) Handles lvwProgress.DoubleClick
With olApp.ActiveExplorer
'// CLEAR SEARCH
.ClearSearch()
'// SWITCH TO SELECTED FOLDER
.CurrentFolder = GetOlFolderFromPath(Me.lvwProgress.Items(Me.lvwProgress.FocusedItem.Index).SubItems(0).Text)
'// DO SEARCH
.Search(String.Concat("received:<", RetentionDate.ToString("MM/dd/yyyy")), Outlook.OlSearchScope.olSearchScopeCurrentFolder)
End With
End Sub
In your code I have noticed multiple dots in the single line of code. It is hard to understand where your code fails if something unexpected happens. So, breaking the chain of property and method calls is essential in troubleshooting such cases.
In the code you change the current folder by setting the CurrentFolder property of the Explorer class. It is a time-consuming operation, so it make sense to wait until it is done. For example, you may try to run the Search method in the Explorer.FolderSwitch event which is fired when when the explorer goes to a new folder, either as a result of user action or through program code.
Also it make sense to do the same operation manually to make sure the filter is correct.

Calling user reference properties in CATIA using VBA

I'm looking to call user referenced properties in CATIA. Currently I am able to do this through a direct path using:
xyz = CATIA.Activedocument.product.UserRefProperties.Item("DESIGNER").Value
MsgBox (xyz),0
I'm looking to generalize so that what ever the user is selecting in the window, that information will be displayed. I'm able to do something similar to what my goal is using code like this:
abc = CATIA.ActiveDocument.Selection.Item(1).Value.Name
MsgBox (abc),0
This gets to my issue. The above code will call system defined properties based on selection, however, this will not work on the user defined properties.
How can I modify this code to take the information stored in a user defined property and display it?
You might have a problem due to the fact that starting at level 2 substructure, your selection does not hold a Reference, but an instance, try this code (I display the 1st User Added Property of the selected product)
MsgBox CATIA.ActiveDocument.Selection.Item(1).LeafProduct.ReferenceProduct.UserRefProperties.Item(1).ValueAsString

Loop through items in "Bar styles", reading items

I'm basically interested in checking if the user is showing any baselines in his active view, and if yes, which one.
If for instance "Baseline1 Start" is used in Bar Styles for the active view, I'd find the matching item number.
If I were able to loop through each bar style item, such as the built-in list MS Project shows lists under "Bar styles", that would solve my problem.
I've tried using the GanttBarEditEx method, but as the documentation explains, it only returns boolean.
If I for instance want to delete an item, this code will do:
GanttBarStyleDelete Item:="41"
My problem is that I don't know what Item I'm looking for. I don't know how to read data about Item:= "41"
This code is not working, but illustrates what I want:
For i = 1 to 200
if GanttBarEditEx(item:=i, from:"Baseline1 start") = True Then MsgBox i
Next
I'm able to figure out the item count using the same logic, when item = i returns an error, that means there's no such item and I have found max. That's how far I've gotten.
There's also a code for GanttBarStyleBaseline which could be of help!
If it's impossible to list the items, I might be able to write a code that's sets each baseline to false, then check if a change was made to the active view, and hence find the active shown baseline...Help?
Update: I noticed that BarBoxStyles opens the "Bar styles" window. But I'm guessing that can't be turned into a collection for looping.

Fundamental Excel VBA Classes & Objects

There is something I am not understanding and I guess it must be pretty basic.
Can someone please be so kind to explain to me the relationship between Classes and Objects enough so that I can understand what is happening below?
Both Location and Name are properties of the PivotTable Class and return strings.
Why do the first statements work but the last 4 give the error
"Object doesn't support this action (Error 445)"?
?ActiveWorkbook.ActiveSheet.PivotTables.Count
3
?ActiveWorkbook.ActiveSheet.PivotTables(1).Name
PivotTable12
?ActiveWorkbook.ActiveSheet.PivotTables(2).Name
PivotTable3
?ActiveWorkbook.ActiveSheet.PivotTables(3).Name
PivotTable2
?ActiveSheet.PivotTables(1).Location
?ActiveSheet.PivotTables(2).Location
?ActiveSheet.PivotTables(3).Location
?ActiveSheet.PivotTables("PivotTable12").Location
[Location Def][1]
[Immediate Window][2]
[Error][3]
Some objects have properties or methods which either aren't available in every version, or in every situation. Seemingly most tasks in VBA can be accomplished in multiple ways; this, it's important to be comfortable with looking for "alternative means of accomplishing the same thing."
In this case my next step would be to check out which properties/methods are available for my object in my scenario by Setting it to a variable:
Dim p As PivotTable
Set p = ActiveSheet.PivotTables(1)
Stop
Run that code, and when execution breaks at the Stop, double click the variable p to select it, right-click it, click Add Watch... and click OK.
This will open the Watches. Use the ⊞ to open and explore the tree to see what's available in this context.
Location likely says "Application Defined error..." however perhaps you can find the location with:
?p.DataBodyRange.Cells.Address
or
?p.DataLabelRange.Cells.Address
...see what the Watches window shows as available within the context you're using.

VB.Net ComboBox (as Dropdown) not translating text to DisplayMember with Databinding

I inherited a fairly large project at work that is undocumented and written in VB (originally started pre .NET, ended around .NET 2). I'm in the process of updating / refreshing a lot of the code, but have run into an annoying issue that I haven't found the solution for yet. This system utilizes a UI, a Web Service, and a SQL DB.
Problem: I have a Databound Combobox (originally set to DropDownList - I'm changing it to DropDown, which is what started this mess - going back isn't an option) that is tied to a DataSet that comes from a Web Service. When a user types in the item they want manually, the data from the text field doesn't seem to associate itself with the DisplayMember, which forces the WS/SQL query to fail (it is sent a blank value when it's expecting a ValueMember). If the user types in a partial selection and then chooses the value they want from the DisplayMember list using the arrow keys or tab, the query goes off without a problem.
My Question: How do I get the text field to translate to the DisplayMember which will then properly tie itself to the ValueMember which will then allow the query to execute correctly? Sorry for making this sound complicated or convoluted; I'm sure the answer is easy and I'm just glazing over it.
The relevant bit of code is:
With cmbDID
If dtsLU.Tables.Contains(reqTable) = True Then
.DataSource = dtsLU.Tables(reqTable)
.DisplayMember = "zip"
.ValueMember = "gridID"
End If
End With
cmbDID.DataBindings.Clear()
cmbDID.DataBindings.Add("SelectedValue", dtsData, strDT & ".gridID")
I've tried changing "SelectedValue" to "Text", which almost works - but it directly translates to gridID and skips zip which ends up with an incorrect Web Service response since the zip and gridID field values are not synced (zip (DisplayMember) may be 5123 while gridID (ValueMember) may be 6047). I've tried changing "SelectedValue" to "SelectedIndex", and that got me no where.
Any help is greatly appreciated.
EDIT
To add some clarification to the process, the below pseudo code / description is roughly what happens. I could post the whole module, but I feel that would just muddy the whole question even more.
Private Sub A
FormAlpha is created with 1 ComboBox in the form of a DropDown
This DropDown is populated with a DataSet
DataBinding with a blank DataSet is added to the control to keep track of the users input
End Sub
lblSubmit_Click event is triggered on FormAlpha by the user after they have populated the DropDown with their data. lblSubmit_Click calls Private Sub Submit
Private Sub Submit
BindingContext(DropDown DataSet, tableName).EndCurrentEdit() is called
DataSet.HasChanges() is processed
If changes are present, changes are processed
HERE lies the problem
If the user has manually typed in the DropDown field, but not hit an arrow key or tab, then the DataSet registers a change, but returns a null value in all fields - it knows something was entered, but that data apparently didn't pass through the DataSet for the ComboBox (ListItems or SelectedIndex didn't change / fire I'm guessing). If the user selects the item with the arrow keys, the DataSet has the proper input (I'm assuming the Data was validated by the control at this point).
If the processed data is good, a value is entered into the database
If the processed data is bad (empty), an error is returned
End Sub
If the above can't be solved with what I've provided, but someone still knows a better way to handle this type of situation, I'm all ears. Rewriting the module isn't ideal, but fixing this problem is a necessity.
Alright, while this fix may not be ideal, it is a fix none the less.
The bare bones problem was that the text value of the DropDown wasn't causing the data to actually affect the SelectedIndex / SelectedValue of the control unless you interacted with it using the arrow keys or a mouse click. So, while the DropDown would read "1234", in reality the control saw "".
The fix I have in place for this is simply calling comboBox.text = comboBox.text whenever the user hits the submit button.