ImageComboBoxEdit selected value not settable - winforms

I'm trying to add an ImageComboBoxEdit control onto a UserControl within my WinForms application.
public ShortCutUserControl()
{
var imageCollection = new ImageCollection { ImageSize = new Size(48, 48) };
imageCollection.Images.Add(Image.FromFile(#"Keyboard\ctrl.ico"));
imageCollection.Images.Add(Image.FromFile(#"Keyboard\alt.ico"));
functionKeyImageComboBoxEdit.Properties.LargeImages = imageCollection;
ImageComboBoxItem ctrlItem = new ImageComboBoxItem
{
Description = "Ctrl",
ImageIndex = 0
};
ImageComboBoxItem altItem = new ImageComboBoxItem
{
Description = "Alt",
ImageIndex = 1
};
functionKeyImageComboBoxEdit.Properties.Items.Add(altItem);
functionKeyImageComboBoxEdit.Properties.Items.Add(ctrlItem);
}
When the control is loaded:
I can't change the currently either directly through code or in the UI.
functionKeyImageComboBoxEdit.SelectedIndex = 0;
I've tried attaching events to the functionKeyImageComboBoxEdit, but none of these seem to be fired/captured;
functionKeyImageComboBoxEdit.SelectedIndexChanged += FunctionKeyImageComboBoxEditOnSelectedIndexChanged;
private void FunctionKeyImageComboBoxEditOnSelectedIndexChanged(object sender, EventArgs eventArgs)
{
//throw new NotImplementedException();
}
What am I missing from my code? I've been looking at the DevExpress ImageComboBoxEdit Documentation but can't see any problem.

The cause of the issue is that you don't set values for ImageComboBoxItems. Do this like:
ImageComboBoxItem ctrlItem = new ImageComboBoxItem
{
Description = "Ctrl",
ImageIndex = 0,
Value = "Ctrl"
};
ImageComboBoxItem altItem = new ImageComboBoxItem
{
Description = "Alt",
ImageIndex = 1,
Value = "Alt"
};

Related

How do I call a control that was created dynamically in c#

First, a great thank you to those who asked/responded to questions. You were able to get me this far.
I wanted to help a young Belgian entrepreneur by taking on a challenge, build a Media managing software to display various media types (Images, Videos, links, text) on huge LED screens.
I have limited coding experience as I work in EDI.
My issue is that I create playlists dynamically based on the number of playlists in the DB (see screenshot), but I cannot trigger the playing of the right playlist when pressing the play button.
Warning, my code is noob code.
PlayList ScreenShot
Label playListLbl = new Label();
GroupBox playListGrp = new GroupBox();
public GroupBox addplayListGrp(int i, int start, int end)
{
GroupBox playListGrp = new GroupBox();
playListGrp.Name = "playListGrp"+ Convert.ToString(1 + i);
playListGrp.Text = "Play list " + Convert.ToString(1 + i);
playListGrp.Font = new Font("Century Gothic", 12F,
FontStyle.Regular, GraphicsUnit.Point, ((byte)(0)));
playListGrp.Width = 425;
playListGrp.Height = 525;
playListGrp.Margin = new Padding(1);
playListGrp.Location = new Point(start, end);
return playListGrp;
}
Button addPlayBtn(int i)
{
Button PlayBtn = new Button();
PlayBtn.Font = new Font("Century Gothic", 9.75F,
System.Drawing.FontStyle.Regular,
System.Drawing.GraphicsUnit.Point, ((byte)(0)));
PlayBtn.ForeColor = Color.Black;
PlayBtn.Location = new Point(10, 467);
PlayBtn.Name = "playBtn" + Convert.ToString(1 + i);
PlayBtn.Size = new Size(100, 30);
PlayBtn.TabIndex = 6;
PlayBtn.Text = "Play";
PlayBtn.UseVisualStyleBackColor = true;
PlayBtn.Click += new EventHandler(playBtn1_Click);
return PlayBtn;
}
public BMS_main()
{
int startPos = 5;
int endPos = 5;
for (int i = 1; i <= playlistCountInc; i++)
{
playListGrp = addplayListGrp(i, startPos, endPos);
playListLbl = addLabel(i);
Label playListLblTime = addLabelTime(i);
Button PlayBtn = addPlayBtn(i);
}
playListGrp.Controls.Add(playListLbl);
playListGrp.Controls.Add(playListLblTime);
playListGrp.Controls.Add(playlistView);
playListGrp.Controls.Add(PlayBtn);
}
private void playBtn1_Click(object sender, EventArgs e)
{
if (ScreenStatus)
{
Playing = true;
DisplayTimer.Stop();
DisplayTimer.Enabled = false;
InitialScreenTimer.Stop();
InitialScreenTimer.Enabled = false;
PlayListTimer.Enabled = true;
PlayListTimer.Start();
}
else
{
message = "Veuillez alimenter les panneaux";
result = MessageBox.Show(message, caption, buttons);
}
public void PlayListTimer_Tick(object sender, EventArgs e)
{
Label lblAcessorio4 =
(Label)playListLbl.Controls.Find("playLbl4",
true).FirstOrDefault();
if (lblAcessorio4 != null)
{
lblAcessorio4.Text = "Test lblAcessorio4";
}
else
{
message = "Label is null";
result = MessageBox.Show(message, caption, buttons);
}
Set the Tag property of your button with something which will help you decide later on which song to play:
playListGrp = addplayListGrp(i, startPos, endPos);
playListLbl = addLabel(i);
Label playListLblTime = addLabelTime(i);
Button PlayBtn = addPlayBtn(i);
// You can do this
PlayBtn.Tag = playListGrp; // or anything else
Then in the button click handler, get the value of the Tag and make a decision based on that. Just keep in mind that whatever you set the Tag to, you will need to cast it back to that type. For example, in the above I set it GroupBox so I will cast it to a GroupBox:
private void playBtn1_Click(object sender, EventArgs e)
{
GroupBox gb = ((Button)(sender)).Tag as GroupBox;
// Now make the decision
if(gb.Name == "whatever you need to put here"){ // do whatever }
}
I would put the lisbox and then get the selected item and play that.

Xamarin.Forms - Detect orientation & adjust page

I'd like to know the orientation of the device (Android, iOS & Windows Phone) at the time I'm building up my page. The page is having a grid with 3 columndefinitions and should have 5 columndefinitions as soon as the orientation got changed to landscape.
Grid grid = new Grid
{
HorizontalOptions = LayoutOptions.Fill,
VerticalOptions = LayoutOptions.Fill,
RowSpacing = 15,
ColumnSpacing = 15,
Padding = new Thickness(15),
ColumnDefinitions =
{
new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) },
new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) },
new ColumnDefinition { Width = new GridLength(1, GridUnitType.Star) }
}
};
for (int i = 0; i < 12; i++)
{
Image img = new Image()
{
Source = "ButtonBlue.png"
};
//if(DependencyService.Get<IDeviceInfo>().IsPortraitOriented())
//{
grid.Children.Add(img, i % 3, i / 3);
//}
//else
//{
// grid.Children.Add(button, i % 5, i / 5);
//}
}
this.Content = new ScrollView
{
Orientation = ScrollOrientation.Vertical,
Content = grid
};
So here I added 12 images to test my code. The page is looking good in portrait-orientation and is having a lot of space between columns if the device is in landscape-orientation.
I'm also trying to use dependency injection to retrieve the information. The DependencyService is doing his job, but I don't have any success retrieving the orientation of the device...
In xamarin.forms, you can get notification from android part by using MessageCenter.
1.In Shared Project
public partial class MyPage : ContentPage
{
public MyPage ()
{
InitializeComponent ();
Stack = new StackLayout
{
Orientation = StackOrientation.Vertical,
};
Stack.Children.Add (new Button { Text = "one" });
Stack.Children.Add (new Button { Text = "two" });
Stack.Children.Add (new Button { Text = "three" });
Content = Stack;
MessagingCenter.Subscribe<MyPage> (this, "Vertical", (sender) =>
{
this.Stack.Orientation = StackOrientation.Vertical;
this.ForceLayout();
});
MessagingCenter.Subscribe<MyPage> (this, "Horizontal", (sender) =>
{
this.Stack.Orientation = StackOrientation.Horizontal;
this.ForceLayout();
});
}
public StackLayout Stack;
}
2.In Android Project
[Activity (Label = "XamFormOrientation.Android.Android", MainLauncher = true, ConfigurationChanges = global::Android.Content.PM.ConfigChanges.Orientation | global::Android.Content.PM.ConfigChanges.ScreenSize)]
public class MainActivity : AndroidActivity
{
protected override void OnCreate (Bundle bundle)
{
base.OnCreate (bundle);
Xamarin.Forms.Forms.Init (this, bundle);
SetPage (App.GetMainPage ());
}
public override void OnConfigurationChanged (global::Android.Content.Res.Configuration newConfig)
{
base.OnConfigurationChanged (newConfig);
if (newConfig.Orientation == global::Android.Content.Res.Orientation.Portrait) {
MessagingCenter.Send<MyPage> (null, "Vertical");
} else if (newConfig.Orientation == global::Android.Content.Res.Orientation.Landscape) {
MessagingCenter.Send<MyPage> (null, "Horizontal");
}
}
}
I solved a similar problem and find it on great post which maybe helpfull for you (see hyperlink below).
In shortcut : Find out orientation by
Page.Width < Page.Height
and use this information in constructor of ContentPage (or other) when creating page
http://www.sellsbrothers.com/Posts/Details/13740

Unable to populate a DataGridViewComboBoxColumn created at design time

I have a DataGridViewComboBoxColumn being craeted at design time.But I want to polulate it at runtime. But it is not happening.
Here is the entire code
public partial class Form1 : Form
{
private List<FileInformation> FileInformationList;
public Form1()
{
InitializeComponent();
PrepareGrid();
DisplayResult();
}
private void PrepareGrid()
{
var fileNameColumn = new DataGridViewTextBoxColumn
{
Name = #"FileName",
HeaderText = "File Name",
DataPropertyName = #"FileName",
AutoSizeMode = DataGridViewAutoSizeColumnMode.Fill,
ReadOnly = false,
Frozen = false
};
dataGridView1.Columns.Add(fileNameColumn);
var downloadColumn = new DataGridViewLinkColumn
{
Name = #"Download",
HeaderText = #"Download",
DataPropertyName = #"Download",
AutoSizeMode = DataGridViewAutoSizeColumnMode.Fill,
ReadOnly = true
};
dataGridView1.Columns.Add(downloadColumn);
var dropdownColumn = new DataGridViewComboBoxColumn
{
Name = #"Test",
HeaderText = #"Country",
AutoSizeMode = DataGridViewAutoSizeColumnMode.Fill,
ReadOnly = true
};
dataGridView1.Columns.Add(dropdownColumn);
}
private void DisplayResult()
{
FileInformationList = LoadItems();
dataGridView1.DataSource = FileInformationList;
((DataGridViewComboBoxColumn)dataGridView1.Columns["Test"]).DataSource = GetCountryList();
((DataGridViewComboBoxColumn)dataGridView1.Columns["Test"]).ValueMember = "id";
((DataGridViewComboBoxColumn)dataGridView1.Columns["Test"]).DisplayMember = "Name";
}
private List<FileInformation> LoadItems()
{
var lstScriptInfo = new List<FileInformation>();
for (int i = 1; i <= 5; i++)
{
lstScriptInfo.Add(new FileInformation { FileName = "File" + i.ToString() + ".txt" });
}
return lstScriptInfo;
}
private DataTable GetCountryList()
{
DataTable CountryDt = new DataTable();
CountryDt.Columns.Add("id");
CountryDt.Columns.Add("Name");
CountryDt.Rows.Add("1", "Canada");
CountryDt.Rows.Add("2", "USA");
return CountryDt;
}
}
public class FileInformation
{
public string FileName { get; set; }
public string Download { get { return "Download File"; } }
}
}
The output is
Please help me to identity what has went wrong?
Two ways to achieve that:
Setting defualt null value for column (skipped null checks):
var cbColumn = (DataGridViewComboBoxColumn)dataGridView1.Columns["Test"];
var ds = GetCountryList();
cbColumn.DataSource = ds;
cbColumn.ValueMember = "id";
cbColumn.DisplayMember = "Name";
cbColumn.DefaultCellStyle.NullValue = ds.Rows[0][0];
cbColumn.DefaultCellStyle.DataSourceNullValue = ds.Rows[0][1];
Second is to iterate after DataBinding and set it manually:
private void DataGridDataBindingComplete(object sender, DataGridViewBindingCompleteEventArgs e)
{
foreach (DataGridViewRow row in dataGridView1.Rows)
{
var hasValue = row.Cells["Test"].Value != null;
if (!hasValue)
{
row.Cells["Test"].Value = 1;
}
}
}
also I'd change binding order:
private void DisplayResult()
{
var cbColumn = (DataGridViewComboBoxColumn)dataGridView1.Columns["Test"];
var ds = GetCountryList();
cbColumn.DataSource = ds;
cbColumn.ValueMember = "id";
cbColumn.DisplayMember = "Name";
cbColumn.DefaultCellStyle.NullValue = ds.Rows[0][0];
cbColumn.DefaultCellStyle.DataSourceNullValue = ds.Rows[0][1];
FileInformationList = LoadItems();
dataGridView1.DataSource = FileInformationList;
}

Load an image into a PictureBox on a different thread

I am trying to load a picture that is fetched on-demand from Google's Static Maps based against a (UK) Post Code.
Lets say I have a client and the clients has an address. One of the properties of client is PostCode. I have a form that loads clients. I feed the client ID to this form's constructor and then use LINQ 2 SQL to load all sorts of information including an address.
private void LoadBranchDetails() {
Text_Update_BI_Name.Text = Branch.BranchNumber;
Text_Update_BI_Manager.Text = String.Format("{0} {1}", Branch.PharmacyManager.FirstName, Branch.PharmacyManager.LastName);
DropDownList_Update_BI_Coordinator.SelectedValue = Branch.CoordinatorID;
DropDownList_Update_BI_ComputerSystem.SelectedValue = Branch.ComputerSystemID;
Text_Update_BI_Phone.Text = Branch.PhoneNumber;
Text_Update_BI_Fax.Text = Branch.FaxNumber;
Address BranchAddress = Branch.Contact.Addresses.FirstOrDefault();
Text_Update_AI_House.Text = BranchAddress.HouseNumber;
Text_Update_AI_Street.Text = BranchAddress.Street;
Text_Update_AI_Area.Text = BranchAddress.Area;
Text_Update_AI_Post.Text = BranchAddress.PostCode;
DropDownList_Update_AI_City.SelectedValue = BranchAddress.City.OID;
MaskedText_Update_OI_NoPharmacist.Value = Branch.NumberOfPharmacists;
MaskedText_Update_OI_NoDispensers.Value = Branch.NumberOfDispensers;
MaskedText_Update_OI_NoMonFri.Value = Branch.NumberOfItemsMondayToFriday;
MaskedText_Update_OI_NoSat.Value = Branch.NumberOfItemsSaturday;
MaskedText_Update_OI_NoSun.Value = Branch.NumberOfItemsSunday;
MaskedText_Update_OI_NoAddicts.Value = Branch.NumberOfAddicts;
MaskedText_Update_OI_NoSupervised.Value = Branch.Supervised;
MaskedText_Update_OI_NoUnsupervised.Value = Branch.Unsupervised;
Check_Update_OI_ConfRoom.Checked = Branch.ConsultationRoom;
try {
PictureGoogleMaps.Image = GoogleAddressInfo.FetchMapInfo(Text_Update_AI_Post.Text).GoogleStaticMap;
} catch (Exception) {
PictureGoogleMaps.Image = Resources.DefaultGoogleMap;
}
}
The line that loads the image into the PictureGoogleMaps causes a hang in UI as the ".GoogleStaticMap" property generates the Google static image when called.
Upon searching the internet, i found this helpful example:
public partial class Form1 : Form
{
public Form1()
{
InitializeComponent();
// Declare a list of URLs and their respective picture boxes
var items = new Dictionary<string, PictureBox>
{
{ "http://www.google.com/logos/spring09.gif", new PictureBox() { Top = 0, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/stpatricks_d4gwinner_eo09.gif", new PictureBox() { Top = 100, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/schiaparelli09.gif", new PictureBox() { Top = 200, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/drseuss09.gif", new PictureBox() { Top = 300, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/valentines09.gif", new PictureBox() { Top = 400, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/unix1234567890.gif", new PictureBox() { Top = 500, Width = 300, Height = 80 } },
{ "http://www.google.com/logos/charlesdarwin_09.gif", new PictureBox() { Top = 600, Width = 300, Height = 80 } },
};
foreach (var item in items)
{
var worker = new BackgroundWorker();
worker.DoWork += (o, e) =>
{
// This function will be run on a background thread
// spawned from the thread pool.
using (var client = new WebClient())
{
var pair = (KeyValuePair<string, PictureBox>)e.Argument;
e.Result = new KeyValuePair<PictureBox, byte[]>(pair.Value, client.DownloadData(pair.Key));
}
};
worker.RunWorkerCompleted += (o, e) =>
{
// This function will be run on the main GUI thread
var pair = (KeyValuePair<PictureBox, byte[]>)e.Result;
using (var stream = new MemoryStream(pair.Value))
{
pair.Key.Image = new Bitmap(stream);
}
Controls.Add(pair.Key);
};
worker.RunWorkerAsync(item);
}
}
}
Now I just need to figure out how to remove the for loop and use this in my scenario. Any ideas?
The sample code comes from this link.
Thanks.
public partial class Form1 : Form
{
private BackgroundWorker imageLoader;
public Form1()
{
InitializeComponent();
this.imageLoader = new BackgroundWorker();
this.imageLoader.DoWork += HandleOnImageLoaderDoWork;
this.imageLoader.RunWorkerCompleted += HandleImageLoaderOnRunWorkerCompleted;
this.LoadUserDetails(1);
}
private void LoadUserDetails(Int32 userID)
{
this.imageLoader.RunWorkerAsync(userID.ToString());
// get the user details
// populate the UI controls with the data....
}
private void HandleImageLoaderOnRunWorkerCompleted(Object sender, RunWorkerCompletedEventArgs e)
{
this.pictureBox1.Image = (Image)e.Result;
}
private void HandleOnImageLoaderDoWork(Object sender, DoWorkEventArgs e)
{
// simulate a web request for an image;
Thread.Sleep(3000);
Image image = Image.FromFile(#"test.jpg");
e.Result = image;
}
}
Also make sure that you show some UI notification that a background operation is in process...something like a initial image (loading.gif) in the PictureBox.
Is it that hard to remove the foreach loop? You only need to load a single picture so remove the foreach loop and pass the url of the picture and the target picturebox to the backgroundworker.

Using a Storyboard animation on a programmatically-added control

I'm trying to fade in a new control to my application's "app" area which is programmatically added after the existing controls are removed. My code looks like this:
void settingsButton_Clicked(object sender, EventArgs e)
{
ContentCanvas.Children.Clear();
// Fade in settings panel
NameScope.SetNameScope(this, new NameScope());
SettingsPane s = new SettingsPane();
s.Name = "settingsPane";
this.RegisterName(s.Name, s);
this.Resources.Add(s.Name, s);
Storyboard sb = new Storyboard();
DoubleAnimation settingsFade = new DoubleAnimation();
settingsFade.From = 0;
settingsFade.To = 1;
settingsFade.Duration = new Duration(TimeSpan.FromSeconds(0.33));
settingsFade.RepeatBehavior = new RepeatBehavior(1);
Storyboard.SetTargetName(settingsFade, s.Name);
Storyboard.SetTargetProperty(settingsFade, new PropertyPath(UserControl.OpacityProperty));
ContentCanvas.Children.Add(s);
sb.Children.Add(settingsFade);
sb.Begin();
}
However, when I run this code, I get the error "No applicable name scope exists to resolve the name 'settingsPane'."
What am I possibly doing wrong? I'm pretty sure I've registered everything properly :(
I wouldn't hassle with the NameScopes etc. and would rather use Storyboard.SetTarget instead.
var b = new Button() { Content = "abcd" };
stack.Children.Add(b);
var fade = new DoubleAnimation()
{
From = 0,
To = 1,
Duration = TimeSpan.FromSeconds(5),
};
Storyboard.SetTarget(fade, b);
Storyboard.SetTargetProperty(fade, new PropertyPath(Button.OpacityProperty));
var sb = new Storyboard();
sb.Children.Add(fade);
sb.Begin();
I solved the problem using this as parameter in the begin method, try:
sb.Begin(this);
Because the name is registered in the window.
I agree, the namescopes are probably the wrong thing to use for this scenario. Much simpler and easier to use SetTarget rather than SetTargetName.
In case it helps anyone else, here's what I used to highlight a particular cell in a table with a highlight that decays to nothing. It's a little like the StackOverflow highlight when you add a new answer.
TableCell cell = table.RowGroups[0].Rows[row].Cells[col];
// The cell contains just one paragraph; it is the first block
Paragraph p = (Paragraph)cell.Blocks.FirstBlock;
// Animate the paragraph: fade the background from Yellow to White,
// once, through a span of 6 seconds.
SolidColorBrush brush = new SolidColorBrush(Colors.Yellow);
p.Background = brush;
ColorAnimation ca1 = new ColorAnimation()
{
From = Colors.Yellow,
To = Colors.White,
Duration = new Duration(TimeSpan.FromSeconds(6.0)),
RepeatBehavior = new RepeatBehavior(1),
AutoReverse = false,
};
brush.BeginAnimation(SolidColorBrush.ColorProperty, ca1);
It is possible odd thing but my solution is to use both methods:
Storyboard.SetTargetName(DA, myObjectName);
Storyboard.SetTarget(DA, myRect);
sb.Begin(this);
In this case there is no error.
Have a look at the code where I have used it.
int n = 0;
bool isWorking;
Storyboard sb;
string myObjectName;
UIElement myElement;
int idx = 0;
void timer_Tick(object sender, EventArgs e)
{
if (isWorking == false)
{
isWorking = true;
try
{
myElement = stackObj.Children[idx];
var possibleIDX = idx + 1;
if (possibleIDX == stackObj.Children.Count)
idx = 0;
else
idx++;
var myRect = (Rectangle)myElement;
// Debug.WriteLine("TICK: " + myRect.Name);
var dur = TimeSpan.FromMilliseconds(2000);
var f = CreateVisibility(dur, myElement, false);
sb.Children.Add(f);
Duration d = TimeSpan.FromSeconds(2);
DoubleAnimation DA = new DoubleAnimation() { From = 1, To = 0, Duration = d };
sb.Children.Add(DA);
myObjectName = myRect.Name;
Storyboard.SetTargetName(DA, myObjectName);
Storyboard.SetTarget(DA, myRect);
Storyboard.SetTargetProperty(DA, new PropertyPath("Opacity"));
sb.Begin(this);
n++;
}
catch (Exception ex)
{
Debug.WriteLine(ex.Message + " " + DateTime.Now.TimeOfDay);
}
isWorking = false;
}
}

Resources