Change text in another application NumericUpDown - c#

I'm a little stuck. I have successfully changed the text in normal TextBoxes in said application but am stuck on changing this one. Im not sure what this is called so I have called it a scroll TextBox, also it will only accept numbers not letters.
The code im using
[DllImport("user32.dll")]
public static extern int SendMessage(IntPtr hWnd, int uMsg, int wParam, int lParam);
const int WM_SETTEXT = 0X000C;
public void Main(IntPtr handle, string text)
{
SendMessage(handle, WM_SETTEXT, 0, 555);
}
I have also tried changing lParam into a StringBuilder which has worked in other TextBoxes but hasnt for this one.
This is the type of TextBox.
Using windows defender there isn't a Edit child like the usual TextBoxes. The only handle I have is for the whole element.
What are my choices here to be able to get that text changed?

The control is known as a NumericUpDown. The text is a representation of the numerical value that it holds, unlike a traditional textbox where you may parse the text to get a number. Depending on your intentions, you may need to find a way to change the underlying numerical value to effectively modify this type of control from another process.

Related

Copy selected text from the CrystalDecisions Report Viewer in Visual Studio

I am writing a Crystal Report viewer in C# Visual Studio. One thing that I have noticed is users want to use Ctrl+C to copy the text they selected (not using the copy button on the viewer). They said it was a feature in a third party application that we switched over from.
How would I achieve this?
I have set the form KeyPreview to true. Using Ctrl+C still does not copy the selected text.
Looping through all of the CrystalReportViewer objects Controls, I have been able to find the control that was highlighted using the Control.Focused getter but there is no indication on which section of that Control contains the highlighted text. That means I cannot even manually copy the text to the clipboard.
I have also tried using the SendMessage PInvoke with WM_COPY, no success.
Here is the code I am using to step through the viewer looking for the correct data and the PInvoke message I am sending.
[DllImport("USER32.DLL", EntryPoint = "SendMessage")]
public static extern IntPtr SendMessage(int hWnd, int Msg, int wParam, IntPtr lParam);
public const int WM_COPY = 0x0301;
CrystalReportViewer viewer;
public void CopySelection()
{
Control.ControlCollection c = viewer.Controls;
GetControl(viewer.Controls);
IntPtr p = SendMessage((int)viewer.Handle, WM_COPY, (int)IntPtr.Zero, IntPtr.Zero);
Console.WriteLine("Copied! " + p);
}
private void GetControl(Control.ControlCollection cItem)
{
foreach (Control c in cItem)
{
if (c.Focused)
Console.WriteLine(c.Focused);
if (c.Controls.Count > 0)
GetControl(c.Controls);
string txt = c.Text;
}
}
Does anybody have any ideas?
Edit:
It seems that after using the 'Find Text' button from the viewer, you are able to copy any text throughout the report with Ctrl+C. Kind of strange. On another note, is there a way to programmatically run the 'Find Text' option?

Attach form window to another window in C#

I want to attach a form to another window (of another process). I try to do this by using
[DllImport("user32.dll", SetLastError = true)]
private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent);
setParentWindow(myWindowHwnd, newParentHwnd);
In doing so my form becomes attached, but is also invisible. Question "Attach window .." solves this issue for a WPF Window, basically by using
HwndSourceParameters parameters = new HwndSourceParameters();
...
HwndSource src = new HwndSource(parameters);
I have tried to transfer this to my form, but I am unable to do so (e.g. how to handle src.RootVisual = (Visual)window.Content; ? -> Complete source).
Another comment says, I need to modify the windows style:
For compatibility reasons, SetParent does not modify the WS_CHILD or WS_POPUP window styles of the window whose parent is being changed. Therefore, if hWndNewParent is NULL, you should also clear the WS_CHILD bit and set the WS_POPUP style after calling SetParent. Conversely, if hWndNewParent is not NULL and the window was previously a child of the desktop, you should clear the WS_POPUP style and set the WS_CHILD style before calling SetParent.
Here I miss the corresponding API for doing so, can I do it directly from C# or have I to use another DllImport again?
Good or evil - SetParent() win32 API between different processes advises against attaching windows in different processes at all, but at least I want to try.
Question:
What would I need to do to get the form window visible? If the approach with WS_Child is the correct one, how would I set it? Or is the WPF approach the way to go, but how would I apply it to an windows form?
-- Findings (later added) --
Modify the windows style of another application using winAPI shows how to modify the style from C# / PInvoke
Find all windows styles here, C# syntax at the bottom.
-- Findings due to discussion with Alan --
I did run my program on Win XP to crosscheck (see Alan's answer below and the comments). At least I do now see something. Since I have added the coordinates as of Alan's examples, my window now shines through in notepad when moving over the other window near the left upper corner. You can still see the text typed in notepad as overlay. Under Win 7 (32) I do see nothing at all.
Now I need to find out whether this can be written in a stable way, appearing on Win 7 as well.
Nevertheless, I still cannot click any buttons on my form, needs to be solved too.
Here is a working example. The hosting app is a simple WinForms application with a blank form (not included here), while the "guest app" has a main form (code behind included below) with some controls, including a test button to display a message after changing the guest form's parent.
The usual caveats linked to in the OP's question apply to this, too.
public partial class GuestForm: Form
{
[DllImport("user32.dll")]
public static extern int SetWindowLong(IntPtr hWnd, int nIndex, int dwNewLong);
[DllImport("user32.dll")]
public static extern int GetWindowLong(IntPtr hWnd, int nIndex);
[DllImport("user32.dll", SetLastError = true)]
private static extern IntPtr SetParent(IntPtr hWndChild, IntPtr hWndNewParent);
public static int GWL_STYLE = -16;
public static int WS_CHILD = 0x40000000;
public GuestForm()
{
InitializeComponent();
}
private void button1_Click(object sender, EventArgs e)
{
MessageBox.Show("done");
}
private void button2_Click(object sender, EventArgs e)
{
Process hostProcess = Process.GetProcessesByName("HostFormApp").FirstOrDefault();
if (hostProcess != null)
{
Hide();
FormBorderStyle = FormBorderStyle.None;
SetBounds(0, 0, 0, 0, BoundsSpecified.Location);
IntPtr hostHandle = hostProcess.MainWindowHandle;
IntPtr guestHandle = this.Handle;
SetWindowLong(guestHandle, GWL_STYLE, GetWindowLong(guestHandle, GWL_STYLE) | WS_CHILD);
SetParent(guestHandle, hostHandle);
Show();
}
}
}
#Horst Walter Hey man, I'm not sure if you've fixed the issue, but I just found a solution to this..
For me the issue was the transparency of the main form you want inside the other form.
Just disable transparency and it should work.

How to show the DropDown list of a ComboBox in WinForms (Telerik)

I'm trying to initiate the drop down list click for a combobox of type MultiColumnComboBox (RadMultiColumnComboBox).
The behavior I'm trying to emulate is when the user clicks the [v] button of the drop down, which shows the actual list.
My control is a Telerik.WinControls.UI.RadMultiColumnComboBox.
I saw a post on the Telerik forums suggesting to do something like this:
Dim item As RadTextBoxItem = TryCast(Me.radMultiColumnComboBox1.MultiColumnComboBoxElement.Children(2).Children(0).Children(0), RadTextBoxItem)
If item IsNot Nothing Then
AddHandler item.Click, AddressOf OnTextBoxItem_Click
End If
Seems like a viable solution, but I'm not sure how this would work on my C# control.
There is also a Win32 hack I found, but this would not pass code review:
// Declare the following in your class
[DllImport("user32.dll")]
public static extern int SendMessage(int hWnd, int msg, int wParam, IntPtr lParam);
public const int CB_SHOWDROPDOWN = 0x14F;
// In the leave event of combobox, use the following code:
SendMessage(comboBox1.Handle.ToInt32(), CB_SHOWDROPDOWN, 1, IntPtr.Zero);
If anyone is familiar with a WinForms ComboBox and can help me figure out how to kick off the Show Items/Elements/List event (or whatever its called), I'd really appreciate it!
The equivalent c# is:
RadTextBoxItem item = this.radMultiColumnComboBox1.MultiColumnComboBoxElement.Children(2).Children(0).Children(0) as RadTextBoxItem;
if (item != null) {
item.Click += OnTextBoxItem_Click;
}
Check if it works for you.
If I understand correctly, you want to open the drop down programatically. If this is the case, here is how you can do that:
radMultiColumnComboBox1.MultiColumnComboBoxElement.ShowPopup();

Clearing A Single Texbox when clicked In C#?

How do i make it so that when a text box is clicked the text that was originally in the text box ("Enter Text Here") is cleared and only the first time it is clicked?
Edit: Sorry, I'm using C#.
The most common way to achieve that is to handle the the textbox's focus event (depending on what framework you're using this will vary) and then test for the expected "tip string". If it's there, then you clear the textbox. If not, you leave it alone.
If you only want to show the "tip" once, then you can unsubscribe from the event after you've handled it.
Note that if you give us some more information about what technology you're using (WinForms/WPF/ASP.NET/MVC/jQuery/HTML5/etc.) then a more specific and possibly more robust approach may be possible.
Assuming its WinForms App, simply bind a handler for the GotFocus or Click event.
I wouldn't follow the suggestion of changing text in GotFocus event - it will cause problems during binding and is not elegant.
WinForms:
There is special technique to set this kind of tooltip for any standard Windows textbox. Declare this:
private const uint ECM_FIRST = 0x1500;
private const uint EM_SETCUEBANNER = ECM_FIRST + 1;
[DllImport("user32.dll", CharSet = CharSet.Auto, SetLastError = false)]
static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, uint wParam, [MarshalAs(UnmanagedType.LPWStr)] string lParam);
and then use:
private void SetWatermark(string watermarkText)
{
SendMessage(this.Handle, EM_SETCUEBANNER, 0, watermarkText);
}
HTML:
<input name="email" placeholder="Enter text here">
What you are trying to do is called "Watermarking" a Text-Box. There are a number of methods do to it:
1) use the MouseClick event on the textbox to remove the Default text.
2) use a ready available class to implement it like the one found here:
http://vidmar.net/weblog/archive/2008/11/05/watermarked-textbox-in-windows-forms-on-.net.aspx
You can find some more info in similar questions asked on Stackoverflow here are a few:
Watermark / hint text / placeholder TextBox in WPF
Watermark in System.Windows.Forms.TextBox
How to use watermark System.Windows.Forms.TextBox using C#?
Hope this was helpful.
Good Luck.
You can do the following:
handle the focus event (Focus) and clear the text if it's the one set
as "tip"
handle the focus lost event (LostFocus) and if the textbox is empty
add the "tip" back to the textbox

How do you change the font used for inline editing of the node text in a WinForms Treeview control?

I am populating a WinForms TreeView control and setting the font attributes of each node differently as they are loaded.
The nodes also allow inline editing (changing the text by pressing F2, or clicking once selected like folder names in Windows Explorer).
When the node goes into edit mode though, the font used when editing reverts to the default font of the TreeView control, not that specific node's font.
Is it possible to set the font of the edit control used when editing each node, to match the font used for displaying that TreeView node? (If so, how?)
As you said, an examination of the TreeNode source reveals that the node is using an Edit Control (from Windows UI Controls, not .NET Forms) when it goes into edit mode. I don't see anything in the class that will set the font in edit mode, so I think you will need to post messages directly to the Edit Control. Use TVM_GETEDITCONTROL to get a handle to it, and WM_SETFONT to set the font. You will probably want Font.ToHfont(), as well.
Edit: here's an example of how you can invoke SendMessage to accomplish the font change.
[DllImport("user32.dll")]
internal static extern IntPtr SendMessage(IntPtr hWnd, uint Msg, IntPtr wParam, IntPtr lParam);
internal const int WM_SETFONT = 0x0030;
internal const int TVM_GETEDITCONTROL = 0x110F;
private void treeView1_BeforeLabelEdit(object sender, NodeLabelEditEventArgs e)
{
TreeNode nodeEditing = e.Node;
IntPtr editControlHandle = SendMessage(treeView1.Handle, (uint)TVM_GETEDITCONTROL, IntPtr.Zero, IntPtr.Zero);
if (editControlHandle != IntPtr.Zero)
{
SendMessage(editControlHandle, (uint)WM_SETFONT, nodeEditing.NodeFont.ToHfont(), New IntPtr(1));
}
}

Categories