- lomoonmoonbird
- Posts: 30
- Joined:
no Constructor found for Commands using MVVM
Hi
I have five files under the same directory in the Assets named mvvmtest (Assets/mvvmtest/ these five files),which are BaseViewModel,FirstModel(role Model),FirstViewModel(role ViewModel),FirstWindow(role View),RelayCommand,to implement MVVM pattern,but there always an error occurring all the time,but if i put FirstViewModel,FirstModel,RelayCommand,BaseViewModel in one file ,like it did http://www.noesisengine.com/docs/Gui.Co ... orial.html, it will work,but when i separate it into modules, although the namespace is correctly referenced,but this error always shows:
These are my implementation:
FirstModel:
BaseViewModel:
FirstViewModel:
RelayCommand:
FirstWindow.xaml:
Any idears ? Thanks in advance.
I have five files under the same directory in the Assets named mvvmtest (Assets/mvvmtest/ these five files),which are BaseViewModel,FirstModel(role Model),FirstViewModel(role ViewModel),FirstWindow(role View),RelayCommand,to implement MVVM pattern,but there always an error occurring all the time,but if i put FirstViewModel,FirstModel,RelayCommand,BaseViewModel in one file ,like it did http://www.noesisengine.com/docs/Gui.Co ... orial.html, it will work,but when i separate it into modules, although the namespace is correctly referenced,but this error always shows:
MissingMethodException: No constructor found for Presentation.Conmmands.RelayCommand::.ctor()
System.Activator.CreateInstance (System.Type type, BindingFlags bindingAttr, System.Reflection.Binder binder, System.Object[] args, System.Globalization.CultureInfo culture, System.Object[] activationAttributes) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System/Activator.cs:319)
System.Activator.CreateInstance (System.Type type, System.Object[] args, System.Object[] activationAttributes) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System/Activator.cs:268)
System.Activator.CreateInstance (System.Type type, System.Object[] args) (at /Users/builduser/buildslave/mono/build/mcs/class/corlib/System/Activator.cs:263)
Noesis.Extend.CreateInstance (IntPtr unityType, IntPtr cPtr) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisExtend.cs:3855)
UnityEngine.Debug:LogException(Exception)
Noesis.Debug:LogException(Exception) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisDebug.cs:24)
Noesis.Error:SetNativePendingError(Exception) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisError.cs:33)
Noesis.Extend:CreateInstance(IntPtr, IntPtr) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisExtend.cs:3875)
System.Object:wrapper_native_000007FED33F9690(String)
NoesisGUISystem:Noesis_LoadXAML(String) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:405)
NoesisGUISystem:Load(String) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:279)
NoesisGUISystem:LoadXaml(String) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:47)
NoesisGUIPanel:LoadXaml() (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:496)
NoesisGUIPanel:OnEnable() (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:383)
NoesisException: Loading Assets/mvvmtest/FirstWindow.xaml
No constructor found for Presentation.Conmmands.RelayCommand::.ctor()
Noesis.Error.Check () (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisError.cs:26)
NoesisGUISystem.Noesis_LoadXAML (System.String xamlFile) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:406)
NoesisGUISystem.Load (System.String xamlFile) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:279)
NoesisGUISystem.LoadXaml (System.String xamlFile) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisGUISystem.cs:47)
NoesisGUIPanel.LoadXaml () (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:496)
NoesisGUIPanel.OnEnable () (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:383)
These are my implementation:
FirstModel:
Code: Select all
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel;
namespace Presentation.Models
{
class FirstModel
{
private string _name;
public string Name
{
get { return _name; }
set
{
_name = value;
}
}
public string ToUpper()
{
return this._name.ToUpper();
}
public bool isValid()
{
return true;
}
}
}
Code: Select all
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.ComponentModel;
namespace Presentation.ViewModels1
{
class BaseViewModel : INotifyPropertyChanged
{
public event PropertyChangedEventHandler PropertyChanged;
public void RaisedPropertyChanged(string prop)
{
var handler = PropertyChanged;
if (handler != null)
{
handler(this, new PropertyChangedEventArgs(prop));
}
}
}
}
Code: Select all
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using Presentation.Models;
using Presentation.Conmmands;
using Presentation.ViewModels1;
namespace Presentation.ViewModels
{
class FirstViewModel : BaseViewModel
{
FirstModel fm;
public Presentation.Conmmands.RelayCommand Button1ToUpperCommand
{
get; set;
}
public FirstViewModel()
{
Console.WriteLine("firstviewmodel initial aaaaaaaaaaaaaaaa");
fm = new FirstModel();
fm.Name = "bakerl";
Button1ToUpperCommand = new Presentation.Conmmands.RelayCommand(ToUpper);
Console.WriteLine(Button1ToUpperCommand);
}
public string textbox1
{
get
{
return fm.Name;
}
set
{
if (fm.Name != value)
{
Console.WriteLine("-------");
fm.Name = value;
RaisedPropertyChanged("textbox1");
}
}
}
public void ToUpper(object parameter)
{
string a = fm.ToUpper();
textbox1 += a;
//fm.Name += textbox1;
Console.WriteLine(a);
}
}
}
RelayCommand:
Code: Select all
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows.Input;
namespace Presentation.Conmmands
{
class RelayCommand : ICommand
{
private readonly Action<object> _action;
public RelayCommand(Action<object> action)
{
_action = action;
}
public event EventHandler CanExecuteChanged
{
add { }
remove { }
}
public bool CanExecute(object parameter)
{
return true;
}
public void Execute(object parameter)
{
_action(parameter);
}
}
}
FirstWindow.xaml:
Code: Select all
<Grid
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:vm="clr-namespace:Presentation.ViewModels"
mc:Ignorable="d"
Height="300" Width="300"
DataContext="{DynamicResource FirstViewModel}">
<Grid.Resources>
<vm:FirstViewModel x:Key="FirstViewModel"></vm:FirstViewModel>
</Grid.Resources>
<Grid>
<StackPanel>
<TextBox Name="textbox1" Text="{Binding textbox1, UpdateSourceTrigger=PropertyChanged}"></TextBox>
<TextBlock Text="{Binding Text, ElementName=textbox1}"></TextBlock>
<Button Name="button1" Content="convert" Command="{Binding Path=Button1ToUpperCommand}"></Button>
<TextBlock Text="{Binding textbox1}"></TextBlock>
</StackPanel>
</Grid>
</Grid>
Re: no Constructor found for Commands using MVVM
The fact that you have RelayCommand in a public setter like this:
Forces you to have a default public ctor in RelayCommand() (or having the setter private with { get; private set; }). This is a limitation of our current architecture that will be solved in 1.3, in that version serialization is going to be eliminated. Another alternative is setting the data context by code, this is the recommended option because you don't pollute the XAML with codebehind classes, making the XAML more portable.
Are you sure it worked whenever you had all the classes in a single file?
Code: Select all
public Presentation.Conmmands.RelayCommand Button1ToUpperCommand
{
get; set;
}
Are you sure it worked whenever you had all the classes in a single file?
- lomoonmoonbird
- Posts: 30
- Joined:
Re: no Constructor found for Commands using MVVM
Hi
I changed
to
but the same error.
And it did work when i put these files into one file.
I changed
Code: Select all
public Presentation.Conmmands.RelayCommand Button1ToUpperCommand
{
get; set;
}
Code: Select all
public Presentation.Conmmands.RelayCommand Button1ToUpperCommand
{
get; private set;
}
And it did work when i put these files into one file.
Re: no Constructor found for Commands using MVVM
Does it work if you add a default ctor to RelayCommand? The solution is not very important because, as said, this is going to change in v1.3
- lomoonmoonbird
- Posts: 30
- Joined:
Re: no Constructor found for Commands using MVVM
Hi
I dont know about ctor,can you specify more about how to do it according to my codes above, thanks.
I dont know about ctor,can you specify more about how to do it according to my codes above, thanks.
Re: no Constructor found for Commands using MVVM
Sorry for my bad explanation. A default constructor, something like this
Code: Select all
class RelayCommand : ICommand
{
private readonly Action<object> _action;
public RelayCommand() {}
public RelayCommand(Action<object> action)
{
_action = action;
}
...
- lomoonmoonbird
- Posts: 30
- Joined:
Re: no Constructor found for Commands using MVVM
Hi
This method i had used before, it also thrown error when click the button
This method i had used before, it also thrown error when click the button
NullReferenceException: Object reference not set to an instance of an object
Presentation.Conmmands.RelayCommand.Execute (System.Object parameter) (at Assets/mvvmtest/RelayCommand.cs:35)
Noesis.Extend.CommandExecute (IntPtr cPtr, IntPtr paramPtr) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisExtend.cs:1545)
UnityEngine.Debug:LogException(Exception)
Noesis.Debug:LogException(Exception) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisDebug.cs:24)
Noesis.Error:SetNativePendingError(Exception) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisError.cs:33)
Noesis.Extend:CommandExecute(IntPtr, IntPtr) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisExtend.cs:1549)
System.Object:wrapper_native_000007FEE4E89810(Int32, Single, Single, Int32)
Noesis.UIRenderer:Noesis_MouseButtonUp(Int32, Single, Single, Int32) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisUIRendererImports.cs:215)
Noesis.UIRenderer:ProcessEvent(Event, Boolean, Boolean) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisUIRenderer.cs:436)
NoesisGUIPanel:OnGUI() (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:456)
NoesisException: Object reference not set to an instance of an object
Noesis.Error.Check () (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisError.cs:26)
Noesis.UIRenderer.Noesis_MouseButtonUp (Int32 rendererId, Single x, Single y, Int32 button) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisUIRendererImports.cs:216)
Noesis.UIRenderer.ProcessEvent (UnityEngine.Event ev, Boolean enableKeyboard, Boolean enableMouse) (at Assets/Plugins/NoesisGUI/Scripts/Core/NoesisUIRenderer.cs:436)
NoesisGUIPanel.OnGUI () (at Assets/Plugins/NoesisGUI/Scripts/NoesisGUIPanel.cs:456)
Re: no Constructor found for Commands using MVVM
Inspecting your XAML, I see one thing that is wrong. The Command syntax is not correct (you must not use the Path keyword).
It should be
Code: Select all
<Button Name="button1" Content="convert" Command="{Binding Path=Button1ToUpperCommand}"></Button>
Code: Select all
<Button Name="button1" Content="convert" Command="{Binding Button1ToUpperCommand}"></Button>
- lomoonmoonbird
- Posts: 30
- Joined:
Re: no Constructor found for Commands using MVVM
Hi
I think its not the Path problem,i created a new unity project , and dragged these files in the folder as same as i did above,i had the Path property in Command binding, and i also didn't have default constructor for RelayCommand, then it worked without any error,strange behaviour,anyway ,Thanks,i think this problem should be tagged with solved. Thanks again.
I think its not the Path problem,i created a new unity project , and dragged these files in the folder as same as i did above,i had the Path property in Command binding, and i also didn't have default constructor for RelayCommand, then it worked without any error,strange behaviour,anyway ,Thanks,i think this problem should be tagged with solved. Thanks again.
-
sfernandez
Site Admin
- Posts: 2991
- Joined:
Re: no Constructor found for Commands using MVVM
Hi,
I replicated your scenario using the latest NoesisGUI 1.2.5f11 and it behaves the same no matter I use several files or a unique file. It always complains about RelayCommand no having a default ctor when playing, because it is serialized into the XAML.
If I change the Button1ToUpperCommand property in FirstViewModel to:
And modify the XAML so it's rebuilt again with the new class definitions (this step is important because otherwise the RelayCommand is still serialized into the file), then I can play your example without problems. I think this last step was the one you missed and why you still got errors.
I hope this helps.
I replicated your scenario using the latest NoesisGUI 1.2.5f11 and it behaves the same no matter I use several files or a unique file. It always complains about RelayCommand no having a default ctor when playing, because it is serialized into the XAML.
If I change the Button1ToUpperCommand property in FirstViewModel to:
Code: Select all
public Presentation.Conmmands.RelayCommand Button1ToUpperCommand
{
get;
private set;
}
I hope this helps.
Who is online
Users browsing this forum: Semrush [Bot] and 49 guests