I'm new to TypeScript and OOP in general. I need to make simple digital clock as homework. I have to use class. It was easier to me to make it in JS, so I did it and it works fine. Now I'm trying to "reverse" it to TypeScript. I also have to add functionality of changing time zones.
Please help!
My working JS version looks like this:
var clock = document.getElementById('clock');
function Clock() {
var time = new Date();
var hours = time.getHours().toString();
var minutes = time.getMinutes().toString();
var seconds = time.getSeconds().toString();
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
clock.textContent = clockStr;
}
Clock();
setInterval(Clock, 1000);
My not working code in TypeScript looks like this:
class Clock {
hours:number;
minutes:number;
seconds:number;
constructor(hours:number, minutes:number, seconds:number) {
this.hours = hours;
this.minutes = minutes;
this.seconds = seconds;
}
print() {
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
}
}
function timeGenerate() {
let time = new Date();
let hours = time.getHours();
let minutes = time.getMinutes();
let seconds = time.getSeconds();
}
function clockRun() {
timeGenerate();
let newClock = new Clock(hours, minutes, seconds);
newClock.print();
}
clockRun();
setInterval(clockRun, 1000);
document.getElementById('tsClock').innerHTML = newClock;
My HTML:
<!DOCTYPE html>
<html lang="">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Typescript Clock</title>
<style>
body {
background-color: royalblue;
font-family: 'Lato';
margin-top: 300px;
text-align: center;
color: ivory;
}
#clock {
font-weight: 300;
font-size: 100px;
}
</style>
</head>
<body>
<h1 id="tsClock"></h1>
<script src="app.js"></script>
</body>
</html>
I'm new to TypeScript and OOP in general. I need to make simple digital clock as homework. I have to use class. It was easier to me to make it in JS, so I did it and it works fine. Now I'm trying to "reverse" it to TypeScript. I also have to add functionality of changing time zones.
Please help!
My working JS version looks like this:
var clock = document.getElementById('clock');
function Clock() {
var time = new Date();
var hours = time.getHours().toString();
var minutes = time.getMinutes().toString();
var seconds = time.getSeconds().toString();
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
clock.textContent = clockStr;
}
Clock();
setInterval(Clock, 1000);
My not working code in TypeScript looks like this:
class Clock {
hours:number;
minutes:number;
seconds:number;
constructor(hours:number, minutes:number, seconds:number) {
this.hours = hours;
this.minutes = minutes;
this.seconds = seconds;
}
print() {
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
}
}
function timeGenerate() {
let time = new Date();
let hours = time.getHours();
let minutes = time.getMinutes();
let seconds = time.getSeconds();
}
function clockRun() {
timeGenerate();
let newClock = new Clock(hours, minutes, seconds);
newClock.print();
}
clockRun();
setInterval(clockRun, 1000);
document.getElementById('tsClock').innerHTML = newClock;
My HTML:
<!DOCTYPE html>
<html lang="">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Typescript Clock</title>
<style>
body {
background-color: royalblue;
font-family: 'Lato';
margin-top: 300px;
text-align: center;
color: ivory;
}
#clock {
font-weight: 300;
font-size: 100px;
}
</style>
</head>
<body>
<h1 id="tsClock"></h1>
<script src="app.js"></script>
</body>
</html>
Share
Improve this question
asked Dec 20, 2017 at 0:22
s-kaczmareks-kaczmarek
1613 silver badges13 bronze badges
4
-
2
TypeScript is a superset of JavaScript, which means all valid JS is valid TS. For starters, the arguments here are all undefined
new Clock(hours, minutes, seconds);
– Phix Commented Dec 20, 2017 at 0:27 - some non typescript magic i made ages ago: gottz.de/uhr.htm gottz.de/binuhr.htm gottz.de/analoguhr.htm – GottZ Commented Dec 20, 2017 at 0:37
- @GottZ this is cool! Can you share code? – s-kaczmarek Commented Dec 20, 2017 at 0:39
- @s-kaczmarek just view the source. thats all the code there is. it's pretty old stuff though. also that vw, vh switch could be replaced with vmin and vmax (css) i did not knew about this at the time. – GottZ Commented Dec 20, 2017 at 11:48
2 Answers
Reset to default 3All valid JavaScript is valid TypeScript, but not the other way around.
In your TypeScript there are some scoping issues.
In the following function, you're declaring 4 variables that only live inside the scope of this function. Returns undefined.
function timeGenerate() {
let time = new Date();
let hours = time.getHours();
let minutes = time.getMinutes();
let seconds = time.getSeconds();
}
Here you're calling the timeGenerate
function which doesn't do anything, creating a new clock with undefined variables, and calling print()
.
function clockRun() {
timeGenerate();
let newClock = new Clock(hours, minutes, seconds);
newClock.print();
}
clockRun();
setInterval(clockRun, 1000);
Here's a working, minimal example (keep it simple!)
class Clock {
// Declare a class variable of type "Element" called el
el: Element;
/**
* Called when "new" is invoked, you'll pass your target element here.
* @param element Target element to update
*/
constructor(element) {
this.el = element;
// Immediately kick off a setInterval to this objects "run" method,
// every 1000ms like you had before.
setInterval(() => this.run(), 1000)
}
/**
* This *could* be in the constructor, but for seperation of duties we'll
* make it a method. This method is invoked every ~1000ms (JavaScript timers
* aren't perfect).
*/
run() {
var time = new Date();
// Don't need to call toString, but it's fine here. When you start
// concatenating numbers onto strings they get converted anyway.
var hours = time.getHours().toString();
var minutes = time.getMinutes().toString();
var seconds = time.getSeconds().toString();
// Your previous logic.
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
// Update this class' "el" variable as before.
this.el.textContent = clockStr;
}
}
// Create a new instance of Clock, passing in your target DOM element.
const clock = new Clock(document.getElementById('clock'))
Codepen
Just before we go through your code. You need to know that typescript can't be read by the browser. So you should pile it to a JavaScript (ES 5). Therefore your index.html should import your piled JavaScript not the typescript file.
Now let's go to your code:
class Clock {
hours:number;
minutes:number;
seconds:number;
constructor(hours:number, minutes:number, seconds:number) {
this.hours = hours;
this.minutes = minutes;
this.seconds = seconds;
this.clockRun();
setInterval(this.clockRun, 1000);
document.getElementById('tsClock').innerHTML = newClock;
}
print() {
if (hours.length < 2) {
hours = '0' + hours;
}
if (minutes.length < 2) {
minutes = '0' + minutes;
}
if (seconds.length < 2) {
seconds = '0' + seconds;
}
var clockStr = hours + ' : ' + minutes + ' : ' + seconds;
}
}
timeGenerate() {
let time = new Date();
let hours = time.getHours();
let minutes = time.getMinutes();
let seconds = time.getSeconds();
}
clockRun() {
this.timeGenerate();
let newClock = new Clock(hours, minutes, seconds);
this.print();
}