I am new in C# and trying to create some controller from my class
But unfortunately it is not showing in the window.
here is my code.
<Window x:Class="SWV_IT_V0._2.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525" Loaded="Window_Loaded">
<Grid x:Name="MainGrid">
</Grid>
</Window>
public partial class MainWindow: Window
{
public MainWindow()
{
InitializeComponent();
}
private void Window_Loaded(object sender, RoutedEventArgs e)
{
TextBlock txtBlock = new TextBlock();
txtBlock.Text = "Hello 1";
MainGrid.Children.Add(txtBlock);
ManageControlers myC = new ManageControlers();
}
}
When run this code I get "Hello 1" on my window
but when i try to create textblock from my class:
namespace SWV_IT_V0._2
{
public partial class ManageControlers : MainWindow
{
public TextBlock txtBlock;
public ManageControlers()
{
txtBlock = new TextBlock();
txtBlock.Text = "Hello 2";
MainGrid.Children.Add(txtBlock);
}
}
}
nothing show in window?
how is it possible to solve this problem?
Thanks in advance.
Try adding InitializeComponent(); to ManageControlersconstructor.
Through ManageControlers myC = new ManageControlers();, you are creating a new instance of your ManageControlers window, but you also need to show it via myC.ShowDialog();.
Related
What I'm attempting to do:
Create a custom page control that consumers can use just like the UWP page, but, that also displays it's own custom content along side the consumers content.
What have I tried:
Creating a new Control, inheriting from Page
Creating a templated control that inherits from page
Creating a control that contains a page
Setting the ContentProperty attribute and binding to it in my custom page
What is the problem?
When I attempt to create a control that has both a xaml and xaml.cs file, that inherits from Page I get InvalidCastExceptions on random controls inside the subclassed control.
Example:
TestPage.xaml
<Page
x:Class="ControlSandbox.TestPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:uwp_toolkit="using:Microsoft.Toolkit.Uwp.UI.Controls"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Page.Content>
<ContentPresenter Content="{Binding}" />
</Page.Content>
<Page.BottomAppBar>
<AppBar Background="Transparent" x:Name="appbar" IsOpen="True">
<uwp_toolkit:InAppNotification x:Name="note">
<StackPanel>
<TextBlock>HEADER!</TextBlock>
<TextBlock>Message</TextBlock>
<StackPanel Orientation="Horizontal">
<Button>OK</Button>
<Button>Cancel?</Button>
</StackPanel>
</StackPanel>
</uwp_toolkit:InAppNotification>
</AppBar>
</Page.BottomAppBar>
</Page>
TestPage.xaml.cs
public partial class TestPage : Page
{
public TestPage()
{
this.InitializeComponent();
}
public void ShowNotification()
{
appbar.IsOpen = true;
note.Show();
}
}
MainPage.xaml
<controlsandbox:TestPage
xmlns:controlsandbox="using:ControlSandbox" x:Class="ControlSandbox.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
Background="{ThemeResource ApplicationPageBackgroundThemeBrush}">
<Grid>
<Button Click="Button_Click">SHOW NOTIFICATION</Button>
</Grid>
</controlsandbox:TestPage>
MainPage.xaml.cs
public partial class MainPage : TestPage
{
public MainPage()
{
this.InitializeComponent();
}
private void Button_Click(object sender, Windows.UI.Xaml.RoutedEventArgs e)
{
this.ShowNotification();
}
}
The above code results in an InvalidCastException and for the life of me I can't find the problem.
System.InvalidCastException: 'Unable to cast object of type
'Windows.UI.Xaml.Controls.AppBar' to type
'Windows.UI.Xaml.Controls.Button'.'
Now if I do the same exact code, but all in the MainPage.xaml instead of in the TestPage.xaml everything works as expected
Update
So I believe this is a bug in the platform. Here is a demo I did of the issue. Please prove me wrong because this would be a real limitation https://github.com/DotNetRussell/UWP_Page_Inheritance_Bug
Update
I added the changes for the answer below. It seems that when I create a normal templated control and put it on a vanilla uwp page, it works fine. However, when I create a templated Page, it ignores my template.
Update
I think this is a bug in the platform. I opened an issue up on github https://github.com/microsoft/microsoft-ui-xaml/issues/1075
The problem is that if create custom base page with Xaml, it will be mandatory converted to the subpage's content, if the sub-page contained controls different with Base page will throw exception. And the better way is create base class without xaml and add the base page content in the code behind. For more code please refer the following .
public class BasePage : Page
{
protected override void OnNavigatedTo(NavigationEventArgs e)
{
this.BottomAppBar = new AppBar()
{
Background = new SolidColorBrush(Colors.Transparent),
IsOpen = false,
Content = new InAppNotification
{
Content = new StackPanel
{
Children =
{
new TextBlock{ Text = "HEADER!"},
new TextBlock{Text = "Message"},
new StackPanel
{
Orientation = Orientation.Horizontal,
Children=
{
new Button{Content = "ok"},
new Button {Content = "cancel"}
}
}
}
}
}
};
base.OnNavigatedTo(e);
}
public void ShowNotification()
{
this.BottomAppBar.IsOpen = true;
InAppNotification note = this.BottomAppBar.Content as InAppNotification;
if (note != null)
note.Show();
}
}
Usage
public sealed partial class MainPage : BasePage
{
public MainPage()
{
this.InitializeComponent();
}
private void Button_Click(object sender, RoutedEventArgs e)
{
ShowNotification();
}
}
Xaml
<local:BasePage
x:Class="CustomPage.MainPage"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:local="using:CustomPage"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
mc:Ignorable="d"
>
<Grid>
<Button Click="Button_Click" Content="ClikMe" />
</Grid>
</local:BasePage>
Create a Templated Control (Project->Add New Item->Templated Control in Visual Studio):
public sealed class CustomPage : Page
{
private AppBar appbar;
private InAppNotification note;
public CustomPage()
{
this.DefaultStyleKey = typeof(CustomPage);
}
protected override void OnApplyTemplate()
{
appbar = GetTemplateChild("appbar") as AppBar;
note = GetTemplateChild("note") as InAppNotification;
}
public void ShowNotification()
{
if (appbar != null)
appbar.IsOpen = true;
note?.Show();
}
}
...and define a custom Style in Themes/Generic.xaml:
<Style TargetType="local:CustomPage">
<Setter Property="BottomAppBar">
<Setter.Value>
<AppBar Background="Transparent" x:Name="appbar" IsOpen="True">
<uwp_toolkit:InAppNotification x:Name="note">
<StackPanel>
<TextBlock>HEADER!</TextBlock>
<TextBlock>Message</TextBlock>
<StackPanel Orientation="Horizontal">
<Button>OK</Button>
<Button>Cancel?</Button>
</StackPanel>
</StackPanel>
</uwp_toolkit:InAppNotification>
</AppBar>
</Setter.Value>
</Setter>
</Style>
There is .xaml.cs file for the CustomPage base class.
Edit: Since the BottomAppBar is not part of the template, you need to wait to access the elements in it until they have actually been created. Just do this in the method:
public sealed class CustomPage : Page
{
public CustomPage()
{
this.DefaultStyleKey = typeof(CustomPage);
}
public void ShowNotification()
{
AppBar appBar = this.BottomAppBar;
appBar.IsOpen = true;
InAppNotification note = appBar.Content as InAppNotification;
if(note != null)
note.Show();
}
}
I have problems understanding the binding to a property in a subclass.
This is my code:
MainWindow.XAML
<Window x:Class="Datagrid_vs_Database.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:local="clr-namespace:Datagrid_vs_Database"
mc:Ignorable="d"
Title="MainWindow" Height="350" Width="525">
<Grid>
<StackPanel>
<TextBlock x:Name="txtPath" Text="{Binding Path=CurrentDatabase.FullFilePath, UpdateSourceTrigger=PropertyChanged}"/>
<Button Command="{Binding openFileBrowser}" Content="New Database"/>
</StackPanel>
</Grid>
Manager.cs
public class Manager
{
private static readonly Manager instance = new Manager();
public static Manager Instance { get { return instance; } }
public IComOpenFileBrowser openFileBrowser { get; private set; }
MainWindow mainWindow;
public Database CurrentDatabase;
private Manager()
{
openFileBrowser = new IComOpenFileBrowser(SaveFileDialog);
CurrentDatabase = new Database();
mainWindow = new MainWindow();
mainWindow.DataContext = this;
mainWindow.Show();
}
private void SaveFileDialog()
{
var sfd = new SaveFileDialog();
sfd.Title = "Choose a filename and a directory to store the new database";
sfd.Filter = "SQLite Database (*.sqlite)|*.sqlite";
if (sfd.ShowDialog() == true)
{
CurrentDatabase.FullFilePath = sfd.FileName;
}
}
}
database.cs
public class Database : INotifyPropertyChanged
{
private string _FullFilePath;
public string FullFilePath {
get {
return _FullFilePath;
}
set { _FullFilePath = value;
NotifyPropertyChanged();
}
}
public event PropertyChangedEventHandler PropertyChanged;
private void NotifyPropertyChanged([CallerMemberName] String propertyName = "")
{
PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
}
}
The thing is when I click on the Button, the SaveFileDialog appears, but when I type in a name and click OK, the Filename does not appear in the Textbox.
BUT: When I set mainWindow.txtPath.DataContext = CurrentDatabase; and delete the "CurrentDatabase." from the XAML code then it works.
I thought that it's correct to set the DataContext of the whole window to the manager class and then access the subclass in XAML by ..{Binding Path= CurrentDatabase.FullFilePath}..
But obviously thats not the case.
Can anybody tell my what I'm misunderstanding here?
I'm trying to make a user control with a dependency property. I need to execute certain logic when the dependency property is changed from outside the usercontrol, but that logic shouldn't execute when the dependency property is changed from inside the user control. I have this small sample. I only want to execute certain logic when the value is set from mainwindow and not when it is set by clicking the checkbox. I don't know if PropertyChangedCallbackis the correct way, but this is what I have.
UserControl:
public partial class UserControl1 : UserControl
{
public int MyProperty
{
get { return (int)GetValue(MyPropertyProperty); }
set { SetValue(MyPropertyProperty, value); }
}
public static readonly DependencyProperty MyPropertyProperty =
DependencyProperty.Register("MyProperty", typeof(int), typeof(UserControl1), new PropertyMetadata(new PropertyChangedCallback(OnPropertyChanged)));
private static void OnPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
// Only process the 5, don't process the 6
}
public UserControl1()
{
InitializeComponent();
}
private void checkBox_Click(object sender, RoutedEventArgs e)
{
MyProperty = 6;
}
}
UserControl xaml:
<UserControl x:Class="WpfApplication4.UserControl1"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
xmlns:d="http://schemas.microsoft.com/expression/blend/2008"
mc:Ignorable="d"
d:DesignHeight="300" d:DesignWidth="300">
<Grid>
<CheckBox x:Name="checkBox" Click="checkBox_Click"/>
</Grid>
</UserControl>
MainWindow:
public partial class MainWindow : Window
{
public int MainWindowProperty { get; set; }
public MainWindow()
{
InitializeComponent();
this.DataContext = this;
MainWindowProperty = 5;
}
}
Mainwindow xaml:
<Window x:Class="WpfApplication4.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
xmlns:local="clr-namespace:WpfApplication4"
Title="MainWindow" Height="350" Width="525">
<Grid>
<local:UserControl1 MyProperty="{Binding MainWindowProperty}"/>
</Grid>
</Window>
private static void OnPropertyChanged(DependencyObject d, DependencyPropertyChangedEventArgs e)
{
if (!disableProcessing)
{
// Only process the 5, don't process the 6
}
}
bool disableProcessing = false;
private void checkBox_Click(object sender, RoutedEventArgs e)
{
disableProcessing = true;
MyProperty = 6;
disableProcessing = false;
}
I implemented the control basics sample from the Kinect for Windows toolkit http://msdn.microsoft.com/en-us/library/dn188701.aspx to control the cursor with a users hand, but when I click on a sub window and then re open the main window with the hand cursor doesn't show.
My question is how do I open a new window without closing the previous window and then navigate back to the same instance of that window, not a new instance?
This is how I call a new window in my main window class:
private void trainingBtn_Click(object sender, RoutedEventArgs e)
{
var newForm = new TrainingFrm(); //create your new form.
newForm.Show(); //show the new form.
this.Close(); //only if you want to close the current form.
}
And this is how I reopen the main window, but it creates anew instance of the main window which I don't want.
private void homeBtn_Click(object sender, RoutedEventArgs e)
{
var newForm = new MainWindow(); //create your new form.
newForm.Show(); //show the new form.
this.Close(); //only if you want to close the current form.
}
What you need is composition
Here how it should look your mainWindow class
public partial class MainWindow : Window
{
private trainingWindow _trainingWindow;
public MainWindow()
{
InitializeComponent();
}
private void buttonGoTraining_Click(object sender, RoutedEventArgs e)
{
if (_trainingWindow== null)
{
_trainingWindow= new trainingWindow(this);
}
this.Visibility = Visibility.Hidden;
_trainingWindow.Show();
_trainingWindow.Visibility = Visibility.Visible;
this.Visibility = Visibility.Hidden;
}
}
and here is your training class
public partial class trainingWindow : Window
{
private MainWindow _mainWindow;
public trainingWindow(MainWindow mainWindow )
{
InitializeComponent();
_mainWindow = mainWindow;
}
private void biuttonBack_Click(object sender, RoutedEventArgs e)
{
this.Visibility = Visibility.Hidden;
_mainWindow.Visibility = Visibility.Visible;
}
}
here is the xaml
<Window x:Class="WpfApplication2.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Grid>
<Button Content="Button" Height="121" HorizontalAlignment="Left" Margin="112,38,0,0" Name="button1" VerticalAlignment="Top" Width="195" Click="buttonGoTraining_Click" />
</Grid>
</Window>
<Window x:Class="WpfApplication2.trainingWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="trainingWindow" Height="300" Width="300">
<Grid>
<Button Content="Button" Height="36" HorizontalAlignment="Left" Margin="52,33,0,0" Name="button1" VerticalAlignment="Top" Width="97" Click="biuttonBack_Click" />
</Grid>
</Window>
Simply hide it, and not close.
If you need to show a fresh information after show, just bind a new data to its view model.
I know my question sounds basic, but i searched all over the place and found nothing..
this is my code :
public MainWindow()
{
InitializeComponent();
Map newMap = new Map();
newMap.setMapStrategy(new SmallMapStrategy());
newMap.createMap();
System.Windows.Forms.PictureBox pictureBox1 = new System.Windows.Forms.PictureBox();
pictureBox1.Paint += new System.Windows.Forms.PaintEventHandler(newMap.grid[3].afficher);
}
this is the afficher function :
public override void afficher(object sender, PaintEventArgs e)
{
e.Graphics.DrawImage(squareImage, pos_x, pos_y, 50, 50);
}
squareImage is an attribute corresponding to a Drawing.Image.
pos_x and pos_y are custom int32 attributes.
What i'd like is to SEE the image while running my application...
Since the PictureBox that you are using is a Winforms Control you will need to add a WindowsFormsHost Control to your Wpf Form and add the PictureBox to that. Any time you dynamically create a control you need to add it to the Form or Container object otherwise it will not be shown.
But first, add these references:
System.Windows.Forms
WindowsFormsIntegration
Now write code something like this.
MainWindow.xaml
<Window x:Class="WpfApplication1.MainWindow"
xmlns="http://schemas.microsoft.com/winfx/2006/xaml/presentation"
xmlns:x="http://schemas.microsoft.com/winfx/2006/xaml"
Title="MainWindow" Height="350" Width="525">
<Grid>
<WindowsFormsHost Height="175" HorizontalAlignment="Left" Margin="10,10,0,0" Name="windowsFormsHost1" VerticalAlignment="Top" Width="255" />
</Grid>
</Window>
MainWindow.xaml.cs
namespace WpfApplication1
{
/// <summary>
/// Interaction logic for MainWindow.xaml
/// </summary>
public partial class MainWindow : Window
{
public MainWindow()
{
InitializeComponent();
System.Windows.Forms.PictureBox picturebox1 = new System.Windows.Forms.PictureBox();
windowsFormsHost1.Child = picturebox1;
picturebox1.Paint += new System.Windows.Forms.PaintEventHandler(picturebox1_Paint);
}
void picturebox1_Paint(object sender, System.Windows.Forms.PaintEventArgs e)
{
System.Drawing.Bitmap bmp = new System.Drawing.Bitmap(#"C:\Temp\test.jpg");
System.Drawing.Point ulPoint = new System.Drawing.Point(0, 0);
e.Graphics.DrawImage(bmp,ulPoint);
}
}
}