I have a simple Silverlight 4 application and have added a child window to it. I am using the below code to open it on a button click. This seems like it should work, does it not?
public void btnAbout_Click(object sender, RoutedEventArgs e)
{
About aboutThis = new About();
aboutThis.Show();
}
The "About" class looks like this:
public partial class About : ChildWindow
{
public About()
{
InitializeComponent();
}
private void OKButton_Click(object sender, RoutedEventArgs e)
{
this.DialogResult = true;
}
private void CancelButton_Click(object sender, RoutedEventArgs e)
{
this.DialogResult = false;
}
}
I don't see any reason why it should not work.
Samples:
http://www.tanguay.info/web/index.php?pg=codeExamples&id=135
http://www.silverlighttoys.com/Tutorials.aspx?tutorial=2
What is your XAML like?
Try setting the Width and Height to 600px by 600px of your About Childwindow from xaml.
Related
I have a Pivot and its header template is a user control and I want to start a continuous Flashing ( Fade Out Fade In ) animation on it on a specific trigger and then also want to stop it on a specific trigger, while both of these triggers/events will happen in the ViewModel of the page. I can take care of the triggers but my only issue is I am not sure how to achieve the infinite flashing behavior. The header has to start flashing when I tell it to and has to keep flashing until I tell it to stop. I wonder if there is some sort of Repeat animation property in xaml but couldn't find that in xaml animations from Community Toolkit
Queue is the model class which defines the context of HeaderTemplate, so I've custom events to start and stop the flashing, because I have access to that Queue object instance within the ViewModel of my page.
All the custom logic happens in code behind of the User Control. Attached is the code I have tried below. I would prefer if this is somehow done all in xaml or mostly in xaml so I can avoid any infinite loops or memory leak risks. My current attempt just freezes the UI and rightly so as I am doing an infinite loop which makes stuff just weird.
Code
Pivot Header
<Pivot.HeaderTemplate>
<DataTemplate x:DataType="cad:Queue">
<dataTemplates:HomePivotHeaderTemplate />
</DataTemplate>
</Pivot.HeaderTemplate>
Queue class
public partial class Queue
{
public event EventHandler<EventArgs> StartFlash;
public event EventHandler<EventArgs> StopFlash;
public void OnStartFlash() => StartFlash?.Invoke(this, EventArgs.Empty);
public void OnStopFlash() => StopFlash?.Invoke(this, EventArgs.Empty);
}
Triggers in ViewModel
public void StartFlashingPendingQueues()
{
PivotQueues.First()?.OnStartFlash();
}
private void StopFlashingPendingQueues()
{
PivotQueues.First()?.OnStopFlash();
}
UserControl for Data Template
public sealed partial class HomePivotHeaderTemplate : UserControl
{
public Queue VM => DataContext as Queue;
private bool _IsFlashing;
private bool _unLoaded;
public HomePivotHeaderTemplate()
{
InitializeComponent();
Loaded += HomePivotHeaderTemplate_Loaded;
Unloaded += HomePivotHeaderTemplate_Unloaded;
DataContextChanged += (s, e) => Bindings.Update();
}
private void HomePivotHeaderTemplate_Unloaded(object sender, RoutedEventArgs e)
{
_unLoaded = true;
Loaded -= HomePivotHeaderTemplate_Loaded;
Unloaded -= HomePivotHeaderTemplate_Unloaded;
VM.StartFlash -= VM_StartFlash;
VM.StopFlash -= VM_StopFlash;
}
private void HomePivotHeaderTemplate_Loaded(object sender, RoutedEventArgs e)
{
VM.StartFlash += VM_StartFlash;
VM.StopFlash += VM_StopFlash;
VM_Flashed();
}
private void VM_StopFlash(object sender, System.EventArgs e) => _IsFlashing = false;
private void VM_StartFlash(object sender, System.EventArgs e) => _IsFlashing = true;
private async Task VM_Flashed()
{
while (true)
{
if (_unLoaded)
{
break;
}
else
{
if (_IsFlashing)
{
await Block.Fade(value: 0f, duration: 500, delay: 0, easingType: EasingType.Linear, easingMode: EasingMode.EaseOut).Then().Fade(value: 1f, duration: 500, delay: 0, easingType: EasingType.Linear, easingMode: EasingMode.EaseIn).StartAsync();
}
}
}
}
}
Edit 1
If I can somehow figure out how to give infinite flashing animation to the textblock I can take care of the rest. basically I could just have 2 textblocks identical, one of them will be flashing other won't, and I can toggle their visibility based on triggers in my viewmodel.
I guess I was just overthinking it. It was a simple DoubleAnimation in a StoryBoard
UserControl code behind
public sealed partial class HomePivotHeaderTemplate : UserControl
{
public Queue VM => DataContext as Queue;
public HomePivotHeaderTemplate()
{
InitializeComponent();
Loaded += HomePivotHeaderTemplate_Loaded;
Unloaded += HomePivotHeaderTemplate_Unloaded;
DataContextChanged += (s, e) => Bindings.Update();
}
private void HomePivotHeaderTemplate_Unloaded(object sender, RoutedEventArgs e)
{
Loaded -= HomePivotHeaderTemplate_Loaded;
Unloaded -= HomePivotHeaderTemplate_Unloaded;
VM.StartFlash -= VM_StartFlash;
VM.StopFlash -= VM_StopFlash;
}
private void HomePivotHeaderTemplate_Loaded(object sender, RoutedEventArgs e)
{
VM.StartFlash += VM_StartFlash;
VM.StopFlash += VM_StopFlash;
}
private void VM_StopFlash(object sender, System.EventArgs e) => FlashStoryBoard.Stop();
private void VM_StartFlash(object sender, System.EventArgs e) => FlashStoryBoard.Begin();
}
UserControl Xaml
<UserControl.Resources>
<Storyboard x:Name="FlashStoryBoard">
<DoubleAnimation Storyboard.TargetName="Block" Storyboard.TargetProperty="Opacity"
Duration="0:0:2"
From="1"
RepeatBehavior="Forever"
To="0.2" />
</Storyboard>
</UserControl.Resources>
<TextBlock x:Name="Block"
Text="{x:Bind VM.Name}" />
I'm trying to select multiple items in a GridView by hovering over them with pressed mouse (like drawing). I tried to achieve this with the PointerEntered event but I'm unable to change the selction from code. Is there a way to implement a custom selection mode?
This didn't work for me because I can't use Style.Triggers in Win RT XAML:
https://stackoverflow.com/a/2886223/5739170
You will have to inherit the gridview control and override the PrepareContainerForItemOverride method:
The code:
public class MyGridView : GridView
{
protected override void PrepareContainerForItemOverride(DependencyObject element, object item)
{
(element as GridViewItem).PointerMoved += MyGridView_PointerMoved;
base.PrepareContainerForItemOverride(element, item);
}
private void MyGridView_PointerMoved(object sender, PointerRoutedEventArgs e)
{
//your logic for setting the isselected
(sender as GridViewItem).IsSelected = true;
}
}
This is how I finally implemented it based on Chirag Shah's answer:
class MyGridView : GridView
{
protected override void PrepareContainerForItemOverride(DependencyObject element, object item)
{
(element as GridViewItem).PointerEntered += SelectItemOnEntered;
(element as GridViewItem).AddHandler(PointerPressedEvent, new PointerEventHandler(SelectItemOnPressed), true);
base.PrepareContainerForItemOverride(element, item);
}
private void SelectItemOnPressed(object sender, PointerRoutedEventArgs e)
{
(sender as GridViewItem).IsSelected = !(sender as GridViewItem).IsSelected;
}
private void SelectItemOnEntered(object sender, PointerRoutedEventArgs e)
{
if (e.Pointer.IsInContact)
(sender as GridViewItem).IsSelected = !(sender as GridViewItem).IsSelected;
}
}
I hope this helps everyone who wants to implement this selection mode.
I can't seem to figure out how to display Account ID and Account Balance into a textbox after the selected index is changed in the listbox. I have a Customer class and a Checking account class(which is a subclass of a Bank Account class). The part of the code that is messing up is at the bottom.
This is the part of my code that I'm having trouble with:
txtAccountID.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetAcctNumber();
txtBalance.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetBalance().ToString();
This is the rest of the code:
public partial class frmStart : Form
{
private static List<Customer_Account> customers;
private Customer_Account aCustomer;
private Saving_Account aSaver;
private static List<Saving_Account> savers;
private Checking_Account aChecker;
private static List<Checking_Account> checkers;
public frmStart()
{
InitializeComponent();
customers = new List<Customer_Account>();
checkers = new List<Checking_Account>();
savers = new List<Saving_Account>();
}
#region New form for Savings and Checking
private void lstFrmStartChecking_DoubleClick(object sender, EventArgs e)
{
//Shows Checking form
frmChecking showCheckingForm = new frmChecking();
this.Hide();
showCheckingForm.ShowDialog();
this.Close();
}
private void lstFrmStartSavings_SelectedIndexChanged(object sender, EventArgs e)
{
//Show Savings form
frmSavings showSavingForm = new frmSavings();
this.Hide();
showSavingForm.ShowDialog();
this.Close();
}
#endregion
#region Everything needed for TabPage1
//Sets CheckChanged event handler for either New customer or Existing Customer
private void rdoNewCustomer_CheckedChanged(object sender, EventArgs e)
{
groupBox2.Visible = true;
groupBox3.Visible = false;
}
private void rdoExistingCustomer_CheckedChanged(object sender, EventArgs e)
{
groupBox3.Visible = true;
groupBox2.Visible = false;
}//End of CheckChanged event handler
//Button controls for Adding customer to our bank and Clearing the textboxes
//in the 1st group panel
private void btnAddCustomer_Click(object sender, EventArgs e)
{
AddCustomerAccountToList();
PopulateListBox(customers);
}
private void AddCustomerAccountToList()
{
double socialSecurity;
double phoneNumber;
double zipCode;
if (double.TryParse(txtTab1SocialSecurity.Text, out socialSecurity) && double.TryParse(txtTab1PhoneNumber.Text, out phoneNumber)
&& double.TryParse(txtTab1Zip.Text, out zipCode))
{
aCustomer = new Customer_Account(txtTab1SocialSecurity.Text, txtTab1Name.Text, txtTab1Address.Text, txtTab1City.Text,
txtTab1State.Text, txtTab1Zip.Text, txtTab1PhoneNumber.Text, txtTab1Email.Text);
customers.Add(aCustomer);
}
else
{
MessageBox.Show("Please be sure to use only numeric entries for: \nSocial Security \nPhone Number \nZip Code", "Non-numeric Entry");
}
}//End of AddCustomerAccount
private void btnTab1Clear_Click(object sender, EventArgs e)
{
foreach (Control ctrl in groupBox2.Controls)
{
if (ctrl is TextBox)
{
((TextBox)ctrl).Clear();
}
txtTab1SocialSecurity.Focus();
}
}//end of button controls for 1st group panel
//Add CheckingAccount to List()
//Populate ListBox for List<>
private void PopulateListBox(List<Customer_Account> aListCustomerAccount)
{
lstTabPage1.Items.Clear();
lstTabPage2Checking.Items.Clear();
foreach (Customer_Account customer in aListCustomerAccount)
{
lstTabPage1.Items.Add(customer.GetCustomerName().ToUpper());
lstTabPage2Checking.Items.Add(customer.GetCustomerName().ToUpper());
}
}//End of Populate listbox
//Search for an existing member with name
private void txtTabPage1Search_TextChanged(object sender, EventArgs e)
{
for (int i = 0; i < lstTabPage1.Items.Count; i++)
{
if (string.IsNullOrEmpty(txtTabPage1Search.Text))
{
lstTabPage1.SetSelected(i, false);
}
else if (lstTabPage1.GetItemText(lstTabPage1.Items[i]).StartsWith(txtTabPage1Search.Text.ToUpper()))
{
lstTabPage1.SetSelected(i, true);
}
else
{
lstTabPage1.SetSelected(i, false);
}
}
}//End of search
//This button will open a checking account for the customer
private void btnOpenCheckingAccount_Click(object sender, EventArgs e)
{
string acctID;
acctID = txtAccountID.Text;
aChecker = new Checking_Account(acctID, DateTime.Today, 0,
200, frmStart.GetCustomer()[lstTabPage1.SelectedIndex]);
}
//This button will open a saving account for the customer
private void btnOpenSavingsAccount_Click(object sender, EventArgs e)
{
aSaver = new Saving_Account(txtAccountID.Text, DateTime.Today, 0, 0.05,
frmStart.GetCustomer()[lstTabPage1.SelectedIndex]);
}
private static List<Customer_Account> GetCustomer()
{
return customers;
}
#endregion
#region Everything Needed for TabPage2
//Search TabPage 2 Checkers
private void txtTabPage2SearchChecking_TextChanged(object sender, EventArgs e)
{
for (int i = 0; i < lstTabPage2Checking.Items.Count; i++)
{
if (string.IsNullOrEmpty(txtTabPage2SearchChecking.Text))
{
lstTabPage2Checking.SetSelected(i, false);
}
else if (lstTabPage1.GetItemText(lstTabPage2Checking.Items[i]).StartsWith(txtTabPage2SearchChecking.Text.ToUpper()))
{
lstTabPage2Checking.SetSelected(i, true);
}
else
{
lstTabPage2Checking.SetSelected(i, false);
}
}
}//End Search TabPage2 Checkers
//Display values in textboxes depending on user selection in listbox
private void lstTabPage2Checking_SelectedIndexChanged(object sender, EventArgs e)
{
try
{
txtTab2SocialSecurity.Text = customers[lstTabPage2Checking.SelectedIndex].GetSocialSecurity().ToString();
txtTab2Name.Text = customers[lstTabPage2Checking.SelectedIndex].GetCustomerName().ToString();
txtTab2City.Text = customers[lstTabPage2Checking.SelectedIndex].GetCity().ToString();
txtTab2State.Text = customers[lstTabPage2Checking.SelectedIndex].GetState().ToString();
txtTab2Zip.Text = customers[lstTabPage2Checking.SelectedIndex].GetZip().ToString();
txtTab2PhoneNumber.Text = customers[lstTabPage2Checking.SelectedIndex].GetPhoneNumber().ToString();
txtTab2Email.Text = customers[lstTabPage2Checking.SelectedIndex].GetEmail().ToString();
txtTab2Address.Text = customers[lstTabPage2Checking.SelectedIndex].GetAddress().ToString();
txtAccountID.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetAcctNumber();
txtBalance.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetBalance().ToString();
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
#endregion
}
(This is what the error message says)
System.ArgumentOutOfRangeException: Index was out of range. Must be non-negative and less than the size of the collection.
Welcome to SO, Guy!
It looks to me that you are appending the .ToString() method to all of your controls except for this one:
txtAccountID.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetAcctNumber();
Change your code to:
txtAccountID.Text = frmStart.GetCustomer()[lstTabPage1.SelectedIndex].GetCheckers()[lstFrmStartChecking.SelectedIndex].GetAcctNumber().ToString();
And you should be fine!
In WP8, they forgot to provide SelectedItem as a dependency property, hence I'm not able to bind to it. I fixed that using this: http://dotnet-redzone.blogspot.com/2012/11/windows-phone-8longlistselector.html
On doing so, I'm noticing that I'm not able to reset the property from the ViewModel, i.e. if I set the item to null in the ViewModel, it does not impact the UI. I have already provided two way binding in the UI but still setting the item to null in the ViewModel does not change the selected item in the LongListSelector. I also don't want to use the SelectionChanged event as I'm sharing ViewModels between WP7.5 app and a WP8 app, hence I want to push as much as I can into the ViewModel. Is there a solution for this?
It appears that the custom LongListSelector class that you are using does not handle the setter properly.
Replace the OnSelectedItemChanged callback with the following:
private static void OnSelectedItemChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var selector = (LongListSelector)d;
selector.SetSelectedItem(e);
}
private void SetSelectedItem(DependencyPropertyChangedEventArgs e)
{
base.SelectedItem = e.NewValue;
}
And there is full version of these two parts:
public class LongListSelector : Microsoft.Phone.Controls.LongListSelector
{
public LongListSelector()
{
SelectionChanged += LongListSelector_SelectionChanged;
}
void LongListSelector_SelectionChanged(object sender, SelectionChangedEventArgs e)
{
SelectedItem = base.SelectedItem;
}
public static readonly DependencyProperty SelectedItemProperty =
DependencyProperty.Register(
"SelectedItem",
typeof(object),
typeof(LongListSelector),
new PropertyMetadata(null, OnSelectedItemChanged)
);
private static void OnSelectedItemChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
var selector = (LongListSelector)d;
selector.SetSelectedItem(e);
}
private void SetSelectedItem(DependencyPropertyChangedEventArgs e)
{
base.SelectedItem = e.NewValue;
}
public new object SelectedItem
{
get { return GetValue(SelectedItemProperty); }
set { SetValue(SelectedItemProperty, value); }
}
}
I have the following code:
private async void SendMsg_Click(object sender, RoutedEventArgs e)
{
RichEditBox.Document.SetText(TextSetOptions.None, "");
await Dispatcher.RunAsync(CoreDispatcherPriority.Normal, () =>
{
if(RichEditBox!=null)
SendBox.Focus(Windows.UI.Xaml.FocusState.Keyboard);
});
}
but when clicked,the RichEditBox didnot got focus.What's wrong with my code? thanks
Sorry,I forgot add this code:"MsgWebView.NavigateToString("Hello World!");".And I found the problem lies in here.So the whole code is like this:
private void SendMsg_Click(object sender, RoutedEventArgs e)
{
MsgWebView.NavigateToString("Hello World!");
SendBox.Focus(Windows.UI.Xaml.FocusState.Programmatic);
}
How to solve this problem?
Best regards.
You need to use the Programmatic option on FocusState (not Keyboard).
SendBox.Focus(Windows.UI.Xaml.FocusState.Programmatic);