Swift Class is not constructible - constructor

I'm following along with the iBook for swift programming, but I am getting an error when I try to contruct a class with var. Here is a stuct and a class:
struct Resolution {
var width = 0
var height = 0
}
class VideoMode {
var resolution = Resolution()
var interlaced = false
var frameRate = 0.0
var name: String?
}
I can create an instance of the Resolution struct just fine, but I can't seem to make one for VideoMode Class.
var r = Resolution()
println("Width:\(r.width) Height:\(r.height)")
r.height = 1234
r.width = 9877
println("Width:\(r.width) Height:\(r.height)")
var vm = VideoMode() //Says that 'VideoMode' is not constructible with ()
let vm = VideoMode() //Apparently this works though.... why?
vm.resolution.width = 22222
vm.resolution.height = 1234
vm.name = "Calimari"
print(vm)
I find this strange can anyone explain?
Update:
Apparently it works ok in playground. I am not running this in playground. I am running it using the master detail template using swift code. I added the "var vm = VideoMode()" in the viewDidLoad method and I get an error. But it seems to be ok if I change it to "let". No clue why that makes a difference.

If you don't define default values for all stored properties then you must define init().
var name: String? // There's no default value here. Either set name to `nil` or define init()
Exerpt from the Swift Documentation:
Classes and structures must set all of their stored properties to an appropriate initial value by the time an instance of that class or structure is created. Stored properties cannot be left in an indeterminate state.
You can set an initial value for a stored property within an initializer, or by assigning a default property value as part of the property’s definition. These actions are described in the following sections.
Addendum:
As stressed by user #valfer, I've found the following:
Optional Property Types
[...] Properties of optional type are automatically initialized with a value of nil, indicating that the property is deliberately intended to have “no value yet” during initialization.
I ignore if the above was present from the get-go or if it was added after the fact as the language is in beta at the time of this writing and is still in flux.

Apparently the Question mark at the end of the "name" variable declaration was preventing this from constructing.
//Implementation file of VideoMode
class VideoMode {
var resolution = Resolution()
var interlaced = false
var frameRate = 0.0
var name: String = "" //removed the question mark
}
//.....in another class
var vm = VideoMode(); //seems to work after making the above changes to the class declaration

I guess you forget to put : NSObject
like this:
class VideoMode: NSObject {
var resolution = Resolution()
var interlaced = false
var frameRate = 0.0
var name: String?
}

Related

Angular 6 - Object Properties Updating without Setting them

I have an editor where the user can edit a product. I save an instance of the product in ngOnInit under initialProduct to make it possible to reset the edits.
Unfortunately, I have a weird issue: When adding a new tag the properties of the initialProduct changes without setting them.
Here is a stackblitz:
https://stackblitz.com/edit/angular-yxrh2d?file=src%2Fapp%2Fapp.component.ts
With this code
this.initialProduct = this.product;
you are assigning to this.initialProduct the same variable positioned at the memory index related by this.product. This because this.product points to a memory address and with the previous operation you are copying only the memory address. So this.product and this.initialProduct point to the same variable.
You need to create another array and to copy this.product values into this.initialProduct (new array).
You can do this by various ways. For example:
// this.initialProduct = this.product;
this.initialProduct = {
tags: Array.from(this.product.tags)
}
or
// this.initialProduct = this.product;
this.initialProduct = {
tags: this.product.tags.concat()
}
or
// this.initialProduct = this.product;
this.initialProduct = {
tags: this.product.tags.slice()
}
because of references
this.tags = this.product.tags;
You can do the following (ES6):
this.tags = [...this.product.tags];

How to call a global var document.getElementById into a function to get the .className

That's what I use to toggle between the Login and Register divs.
The following is actually working:
function myNavLogin()
{
document.getElementById("Content-Login").className = "Content-On";
document.getElementById("Content-Register").className = "Content-Off";
}
I want to call the next global variable:
var divLogin = document.getElementById("Content-Login");
var divRegister = document.getElementById("Content-Register");
Inside the function like this way:
function myNavLogin()
{
divLogin.className = "Content-On";
divRegister.className = "Content-Off";
}
The second example isn't working, I think because the variable isn't declared by the correct way or I am calling it bad... please help, thanks.
Regards, Chicler ;)
Your question is probably a simple variable scoping one, but here's a more thorough response anyway. Global variables are a horrible way to code. You should try to use a more object oriented approach. You should also consider keeping tag names out of your variable names, since markup is apt to change. Finally, when toggling classes, it's better to simply add and remove an "on" state and have the "off" state be the default. Here's an example:
var AccountLogic = function(){
this.elLogin = document.getElementById("Content-Login");
this.elRegister = document.getElementById("Content-Register");
this.login = function(){
this.elLogin.classList.add("content-on");
this.elRegister.classList.remove("content-on");}
}
}
var accountLogic = new AccountLogic();

Referencing binding annotations dynamically in Polymer 1

I'm trying to set up a function in Polymer 1.0 which will allow a JSON response to tell my application which {{BindingVariable}} in which to insert the response. Unfortunately, the syntax for referencing these binding variables seems to be similar to this:this.BindingVariable, which doesn't allow for dynamic variable names.
What I really need is a way to reference these dynamically like how we can reference anything else in the DOM/PolyDOM. For example: document.querySelector('#'+elementID).
Is there any way to reference binding annotations dynamically? I've searched through the entire Polymer DOM and can't find them listed anywhere even though I know they're in the page.
example
app._onResponseRetrieved = function(e) {
for (var key in e.detail.response) {
// none of these work, but they demonstrate what I'm trying to accomplish
// this.key = e.detail.response[key];
// this.querySelector(key) = e.detail.response[key];
// window[key] = e.detail.response[key];
// document[key] = e.detail.response[key];
// Polymer.dom(key) = e.detail.response[key];
}
JSON Sent to _onResponseRetrieved
{"contactFormOutput":"Success!"}
Binding Annotation in index.html
<div>{{contactFormOutput}}</div>
this[key] = e.detail.response[key];
Javascript allows [] on any object for dynamic property referencing

iOS DatePicker binding gives MvxBind:Error for viewmodel => view direction

I am using an iOS UIDatepicker (weekendOnTimepick) in 'time only'mode in one of my views that needs to update the properties in my Viewmodel whenever the Picker view is changed. The direction Viewmodel => view is only important at View load hence is treated outside of the binding (see code below).
Although this works great (after overcoming the challenges of iOS wrt time localisation), I get a message "MvxBind:Error: 86.61 Problem seen during binding execution for binding Time for TimerOnWeekend - problem ArgumentException: Object type System.DateTime cannot be converted to target type: MonoTouch.Foundation.NSDate"
I guess this has to do with the binding direction I'm not using and doesn't seem to be an issue, but I do fear it will bring some sort of instability to my app.
Question : is this the right way of achieving the goal stated above, or would it be better to for instance ditch binding alltogether and use a View to Viewmodel subscription message with every Datepicker update ?
public override void ViewDidLoad ()
{
base.ViewDidLoad ();
_userSettings = Mvx.Resolve<IHpRepository>().HpFullData.UserSettings;
var set = this.CreateBindingSet<TimerView, TimerViewModel>();
// TODO: check timepicker binding
set.Bind(weekendOnTimepick).For("Time").To(vm => vm.TimerOnWeekend);
int weekendOnHr = _userSettings.TimerOnWeekend / 3600 ;
int weekendOnMin = (_userSettings.TimerOnWeekend % 3600) / 60;
var weekendOnTime = new DateTime (2014, 1, 1, weekendOnHr, weekendOnMin, 0);
var AdjweekendOnTime = weekendOnTime.ToUniversalTime ();
weekendOnTimepick.SetDate (TouchConverter.DateTimeToNSDate(AdjweekendOnTime),true);
set.Apply();
}

Accessing DOM object properties from Chrome's content script

I ran into a strange problem with a content script. The content script is defined as "run_at" : "document_end" in the manifest. After a page is loaded the script inserts an object tag into the page (if the tag with predefined id does not exist yet), and sets some properties in it, such as type, width, height, innerHTML, and title. All works fine here.
function checkForObject()
{
var obj = document.getElementById("unique_id");
if(obj == null)
{
var d = document.createElement("object");
d.id = "unique_id";
d.width = "1";
d.height = "1";
d.type = "application/x-y-z";
d.title = "1000";
d.style.position = "absolute";
d.style.left = "0px";
d.style.top = "0px";
d.style.zIndex = "1";
document.getElementsByTagName("body")[0].appendChild(d);
}
}
checkForObject();
I see the new object in the page html-code with proper values in its properties.
Some time later I need to read the title property of the object in the same content script. The code is simple:
function ReadTitle()
{
var obj = document.getElementById("unique_id");
var value = obj.title; // breakpoint
console.log(value);
// TODO: want to use proper title value here
}
The function is called from background.html page:
chrome.tabs.onActivated.addListener(
function(info)
{
chrome.tabs.executeScript(info.tabId, {code: 'setTimeout(ReadTitle, 250);'});
});
Unfortunately, in ReadTitle I'm getting not what I expect. Instead of current value of the title I see the logged value is:
function title() { [native code] }
If I set a breakpoint at the line marked by // breakpoint comment, I see in the watcher that all object properties including the title are correct. Nevertheless, the variable value gets the abovementioned descriptive string.
Apparently, I have missed something simple, but I can't figure it out.
The answer. It was a bug in the npapi plugin, which hosts the object of used type. My apologies for all who have read the question with intention to help.
The NPAPI plugin used in the object erroneously reported title as supported method.