Saturday 28 December 2019

Here's Why You Shouldn't Take Tech Career Advice From Your Friends

During the last Chinese New Year, I got this link in my news feed, an article from Robert Half, a recruitment agency. It caught my eye for the wrong reasons. Something about this article struck me as extremely problematic.

If you’re not sure where you want your career to go, don't be afraid to seek help. Ask friends and family over Chinese New Year for their advice.


Really? I call bullshit.


Surround yourself with friends...
but don't take their advice. Because
their advice sucks.

Friends are good things to have. They hang out with you when company is needed, they usually find the same things funny, and they listen when you need to rant. But friends are not infallible (big surprise, huh?) and when you need advice, sometimes they fall short. I don't mean they run out of advice; advice is primarily opinion-based, and if it's one thing human beings rarely run out of, it's opinions. I'm going to be really blunt here and say this - don't listen to your friends. Especially when it comes to a tech career. Your friends don't know shit. This goes for your parents and your siblings as well.

Now let's just be unambiguously clear about one thing. I'm laboring under the assumption that your friends care, and only want the best for you. They honestly are telling you what they think is the best way to go. They're not jealous of you, or trying to sabotage you. They have only the purest of intentions.

And their advice is still utter bollocks.

I have a lot of friends, and I've lost count of the number of times I've had to dismiss their freely offered opinion as well-meaning, but useless. That's because most of them are non-technical people and not of the career consultant variety. I'm honestly baffled at the number of people who have seen fit to advise me on how to build my career in my own industry without having worked a single day in it. Or people who give me marriage advice when they don't even have someone to hold hands with. Or people who tell me how to manage my money when they're the ones who are constantly in debt.

Advice is easy to give, and exceedingly few people will, when dishing out advice of any sort, pause to consider if they are qualified to dispense that particular brand of wisdom. That's not a blot on their character; merely an unfortunate facet of human nature.

But the advice is free!

Oh, dear. You know what else is free? Farts. Toe fungus. STDs. You don't have to pay a cent for them either, but do you really want those?

Advice is one of those things you should not value just because it's freely given. If it was worth anything professionally, you should have to seek it out, or better still, pay for it.

But my friend is a well-paid developer in a tech company!

Then yes, listen to him. Or her. But you should be listening because this friend is an authority in the career you want, and not because he or she is your friend. In fact, if you're in the habit of listening to people just because they're your friends, stop it. Pronto.

But they've hired techs before!

Oh, wow. I guess that must really mean they know something, huh?

Hey, you know who else has hired techies? Human Resource people, who (surprise, surprise) may not actually know all that much about tech careers specifically. Clueless CEOs of small outfits who don't have the sense to leave hiring to more qualified people. Incidentally, unless you're desperate, I'd steer clear of those companies.

I'm not saying that people who have hired techies don't know shit. They could actually know shit. But if they claim to know shit and don't want to get laughed at, they should also know that "I've hired techs before", on its own, doesn't cut the fucking mustard.

Actually, scratch that last bit. They don't have to know. You do.

What about my ex-classmates from my Computer Science Degree?

That depends. Are they currently making a living in tech? Then go for it. If not, fuck 'em. What could you possibly learn about the tech industry from people who haven't written a single line of code in years? I'm sure their opinions are valuable to someone, somewhere out there. Just not to you.

Why Advice Can Be Bad

The best advice doesn't necessarily come from someone in your field, but it helps.

People who are only in it for the money, will give you advice on how to earn money in the shortest time possible. People who just want to coast along in life, will naturally recommend jobs where you can take it easy. People who equate professional success with fancy titles will point you the way to companies where you can make a name for yourself and climb the ladder.

None of that is intrinsically wrong. People want what they want. But you need to be really honest and ask yourself if this is what you want. Just because what people want for themselves isn't wrong, it doesn't follow that what they want for themselves must be right for you.

Don't follow for the
sake of following.

I'll say this again - advice is opinion-based. And opinions are skewed by perspective. If you're looking for relevant career advice regarding the tech industry, do you think you could obtain it from someone plying his or her trade in, say, healthcare? Law? Journalism? Sales and marketing? Driving a cab? Running a hipster cafe? A career soldier or civil servant?

None of the above, Junior.

The point is that the person giving you the advice should have his career goals aligned to yours. He should want the same things you do, and preferably already accomplished them. Therefore it follows that someone in the industry you want to build your career in, would give you better advice than someone out of it. If you want a tech career, be advised by a tech.

It could still be bad advice, but it would at least be relevant bad advice.

And even then, bear in mind that the advice isn't good just because the one giving it comes from the same industry. There's this guy who used to intern at a start-up I worked for. He wants to be a software architect five years down the road, and the worst thing he could do is listen to me. Why? Because I'm not the kind of guy who wants to be a software architect. I want to code. I don't want to be in the position of overseeing something and then not getting my hands dirty. Any advice I give him would not bring him anywhere close to his goal. It would only bring him close to my goal. And even then, I'm hardly the ideal person to ask - I've made several mistakes during my storied career and will likely make several more by the time this post is read.

But if I'm not convincing enough, maybe this long-dead technopreneur will be.
"Your time is limited, so don't waste it living someone else's life." - Steve Jobs

The times I didn't listen...

A couple years ago, I was in the market for a job. A few people, rather amusingly, offered me tips on my job search. Apparently, I needed to:

- refuse to provide details of my last drawn pay (to give me that edge in negotiation)
- provide some plausible bullshit for leaving my last job (because the truth would blunt my edge in negotiation)
- cover up the tattoos on my fingers. (because, even though it was 2017, these things somehow still matter)

Liverpool FC pride, baby.

You know what I did? None of that shit. I was too arrogant to lie, obfuscate or provide evasive answers. I provided excruciatingly detailed salary figures from all my previous places of employment. I stated up front that the last two companies that I worked in, tanked. And I certainly didn't cover up my goddamn fingers.

I not only landed the job, but they offered me more than what I had asked for.

Strategy? Bah humbug. You need substance, not strategy. You need to have a finely honed sense of what matters and what doesn't. Without that, no amount of "strategy" proposed by people who can't tell Java from JavaScript, will help you. Trust your instincts.

In conclusion

Be very stringent as to whom you take advice from.

Whatever advice you take, remember this. This is your career. Own it. It is your responsibility. You don't get to do something stupid and then claim that people gave you bad advice. You chose to follow it!

You're the only one with skin in the game. If you're going to give your career an honest shot, I hope to hell that whoever is advising you has something a lot more substantial than "I'm older than you, so I know better" and "I mean well".

Also remember that everyone has a right to their opinion, informed or otherwise. What they don't have an automatic right to, is to be taken seriously by you. That they have to earn. And if you choose to give their opinion weight simply because they're family or friends... hey, you know what they say - there's a sucker born every minute.


You've been so advised,
T___T

Sunday 22 December 2019

Web Tutorial: Christmas Tree SVG Animation

Merry Christmas, readers!

For this month's web tutorial, let's do something light and fun. We'll be playing with Scalable Vector Graphics, SVG for short! SVG has been around a long time, but it is only with HTML5 that we get to embed them in HTML pages. They're different from CSS-rendered graphics, but totally compatible with CSS styling. In fact, there are many parallels.

It's really easy, if you're prepared to do a bit of simple arithmetic. Really simple arithmetic.

Without further ado, here's some HTML.
<!DOCTYPE html>
<html>
    <head>
        <title>Xmas SVG</title>

        <style>
       
        </style>
    </head>

    <body>

    </body>
</html>


Add in an svg tag. Yep, it's that simple! Then add some text in there. This should not show up on your browser, but in the event you come across a browser that's so backward it doesn't support SVG (yes, Internet Explorer, I'm looking at you), the text will be displayed.
<!DOCTYPE html>
<html>
    <head>
        <title>Xmas SVG</title>

        <style>
       
        </style>
    </head>

    <body>
            <svg>
                SVG not supported
            </svg>
    </body>
</html>


Let's do some styling. Set the body background to a dark blue, then give the svg element a height, width and a red outline.
        <style>
            body
            {
                background-color: rgba(0, 0, 50, 1);
            }

            svg
            {
                width: 500px;
                height: 500px;
                outline: 0px solid #FF0000;
            }
        </style>


Here's your SVG. We'll start drawing next.


OK, this may be counter-intuitive, but we will jump right into drawing a path - the shape of a Christmas tree. The cool thing about SVG is that unlike CSS, you don't have to divide complex shapes into rectangles and circles and figure out clever ways to make it work. Nope, you just draw a path. Like so. Give it a class of tree while you're at it.
            <svg>
                <path class="tree" />
                SVG not supported
            </svg>


Now remember you're drawing an SVG, so the usual CSS attributes don't apply. Here, we define the thickness of the lines using the stroke-width property, and set the line color to a basic green. You could define stroke and stroke-width as attributes within the path tag itself, but that's just messy.
            svg
            {
                width: 500px;
                height: 500px;
                outline: 1px solid #FF0000;
            }

            .tree
            {
                stroke: rgba(0, 255, 0, 1);
                stroke-width: 1;
            }


In the SVG, the d attribute is a string of commands we'll use to define the path. I broke up the line into several lines for clarity. It's about to get a lot longer. First, we use "M 250 100" which means "move to x-coordinate 250 and y-coordinate 100". For reference, the top left corner of the SVG is (0, 0). Since the SVG is 250 pixels wide and tall, (250, 100) is horizontally right in the middle and vertically near the top. This point is the top of the tree.
            <svg>
                <path d="
                M 250 100"
                class="tree"/>
                SVG not supported
            </svg>


Next, draw a line to the next point, somewhere left to the starting point and lower. For this, you use "l". It stands for "line", as in, "line to x minus 30, y plus 30 from the last specified point". The lower case "l" allows us to specify the instructions relative to the last point. You can use an uppercase "L", but then you'd have to specify the absolute coordinates (220, 70) which doesn't sound too bad right now, but can be a huge pain in the butt if you need to move the tree later on.
            <svg>
                <path d="
                M 250 100
                l -30 30
                "
                class="tree"/>
                SVG not supported
            </svg>


So yeah, you see what you've done? You've created a green line from (250, 100) to (220, 70).


Let's specify another line. The next one doesn't move vertically, but is 10 pixels right from the last point.
            <svg>
                <path d="
                M 250 100
                l -30 30 l 10 0
                "
                class="tree"/>
                SVG not supported
            </svg>


Now you see you've drawn a horizontal line from the last point. Do you see the black background there? That's because we never specified a background color for the path, so it's defaulting to that color. Leave it alone for now.


Here's one side of the tree drawn for you.
                <path d="
                M 250 100
                l -30 30 l 10 0
                l -30 30 l 10 0
                l -30 40 l 10 0
                l -40 50 l 10 0
                l -40 70 l 10 0
                l -40 80 l 320 0
                " class="tree"/>


See it taking shape?


Let's complete the drawing.
                <path d="
                M 250 100
                l -30 30 l 10 0
                l -30 30 l 10 0
                l -30 40 l 10 0
                l -40 50 l 10 0
                l -40 70 l 10 0
                l -40 80 l 320 0
                l -40 -80 l 10 0
                l -40 -70 l 10 0 
                l -40 -50 l 10 0
                l -30 -40 l 10 0
                l -30 -30 l 10 0
                l -30 -30
                " class="tree"/>


Ah. Spectacular!


To color the tree, we use the fill property. We'll set it to a muted green.
            .tree
            {
                stroke: rgba(0, 255, 0, 1);
                stroke-width: 1;
                fill: rgb(0, 100, 0);
            }


The tree's been drawn! But it looks a bit stiff...


What this tree needs is curves. Instead of "l", use "q". That's "q" as in "Quadratic Bézier curve". It still draws a line to the point specified, but two new numbers, namely, 0 and 10, form the arguments. The first number is how much the line will curve towards the x-axis, while the second number is how much the line will curve towards the y-axis. In this case, "0" means that no action is taken along the x-axis while the line dips slightly about "10" pixels vertically.
                <path d="
                M 250 100
                q 0 10 -30 30 l 10 0
                l -30 30 l 10 0
                l -30 40 l 10 0
                l -40 50 l 10 0
                l -40 70 l 10 0
                l -40 80 l 320 0
                l -40 -80 l 10 0
                l -40 -70 l 10 0 
                l -40 -50 l 10 0
                l -30 -40 l 10 0
                l -30 -30 l 10 0
                l -30 -30
                " class="tree"/>


See the curve at the top?


The rest of it has been done for you. Experiment! Quadratic Bézier curves aren't the point of this tutorial today, and they aren't that important right now. But they sure do make things prettier.
                <path d="
                M 250 100
                q 0 10 -30 30 l 10 0
                q 0 10 -30 30 l 10 0
                q 0 20 -30 40 l 10 0
                q 0 20 -40 50 l 10 0
                q 0 30 -40 70 l 10 0
                q 0 40 -40 80 l 320 0
                q -40 -40 -40 -80 l 10 0
                q -40 -30 -40 -70 l 10 0 
                q -30 -20 -40 -50 l 10 0
                q -20 -10 -30 -40 l 10 0
                q -20 -10 -30 -30 l 10 0
                q -20 -10 -30 -30
                " class="tree"/>


Nice curves!


The Star

So now you've drawn a tree-shaped path and colored it. Let's draw a circle at the top of the tree. The center of the circle is defined by the cx and cy attributes. They've been set to the coordinates of the topmost point of the tree. The radius is defined by the attribute r. In this case, it's 5 pixels. We'll set the rest of the circle using the toplight CSS class.
                <circle cx="250" cy="100" r="5" class="toplight">

                </circle>

                <path d="
                M 250 100
                q 0 10 -30 30 l 10 0
                q 0 10 -30 30 l 10 0
                q 0 20 -30 40 l 10 0
                q 0 20 -40 50 l 10 0
                q 0 30 -40 70 l 10 0
                q 0 40 -40 80 l 320 0
                q -40 -40 -40 -80 l 10 0
                q -40 -30 -40 -70 l 10 0 
                q -30 -20 -40 -50 l 10 0
                q -20 -10 -30 -40 l 10 0
                q -20 -10 -30 -30 l 10 0
                q -20 -10 -30 -30
                " class="tree"/>


Here, we define a bright yellow (almost white) border at a very low opacity, and the fill is the same color but at higher opacity. The border width is 15 pixels.
            .tree
            {
                stroke: rgba(0, 255, 0, 1);
                stroke-width: 1;
                fill: rgb(0, 100, 0);
            }

            .toplight
            {
                stroke: rgba(255, 255, 200, 0.3);
                stroke-width: 15;
                fill: rgba(255, 255, 200, 0.8);
            }


Note that there are no z-index properties for SVGs. Whatever element comes first is covered by anything that is drawn over it. Which is pretty damn convenient under certain conditions!


Let's animate that!

Use the animate tag within the circle tag. The attributeName attribute defines the attribute that will be animated. It's "r". The from and to attributes determines what values the animation will change "r" to, And the dur attribute defines how long the entire animation takes. Let's set it to half a second. The repeatCount attribute, set to "indefinite", means that the animation will repeat forever.

Refresh your browser. The circle at the top will appear to be blinking rapidly! That's because it's growing from 4 pixels radius to 6 pixels radius every half a second.
                <circle cx="250" cy="100" r="5" class="toplight">
                    <animate attributeName="r" from="5" to="6" dur="0.1s" repeatCount="indefinite" />
                </circle>


Time for some decorations...

We'll draw another circle. Place it anywhere within the Christmas Tree, make it as large as you want, and style it using the CSS class ball.
                <path d="
                M 250 100
                q 0 10 -30 30 l 10 0
                q 0 10 -30 30 l 10 0
                q 0 20 -30 40 l 10 0
                q 0 20 -40 50 l 10 0
                q 0 30 -40 70 l 10 0
                q 0 40 -40 80 l 320 0
                q -40 -40 -40 -80 l 10 0
                q -40 -30 -40 -70 l 10 0 
                q -30 -20 -40 -50 l 10 0
                q -20 -10 -30 -40 l 10 0
                q -20 -10 -30 -30 l 10 0
                q -20 -10 -30 -30
                " class="tree"/>

                <circle cx="270" cy="150" r="5" class="ball">

                </circle>


Here, we will give ball an orange outline, 1 pixel thick. For the fill property, we will use an SVG-defined value. It's represented with a hash sign and the value name, which is "ballGradient".
            .tree
            {
                stroke: rgba(0, 255, 0, 1);
                stroke-width: 1;
                fill: rgb(0, 100, 0);
            }

            .ball
            {
                stroke: rgba(255, 200, 100, 0.3);
                stroke-width: 1;
                fill: url(#ballGradient);
            }

            .toplight
            {
                stroke: rgba(255, 255, 200, 0.3);
                stroke-width: 15;
                fill: rgba(255, 255, 200, 0.8);
            }


You should now see an orange circular outline near the top of the tree.


Now let's define the fill, ballGradient. We first create a defs tag.
            <svg>
                <defs>

                </defs>

                <circle cx="250" cy="100" r="5" class="toplight">
                    <animate attributeName="r" from="5" to="6" dur="0.1s" repeatCount="indefinite" />
                </circle>


Within this tag, create a radialGradient tag with an id of ballGradient.
                <defs>
                    <radialGradient id="ballGradient">

                    </radialGradient>
                </defs>


Let's fill in these attributes. fx and fy define the center point of the innermost circle. In our case, we want it horizontally to the left, and vertically middle. cx and cy define the center point of the outermost circle. I'm gonna place this right in the middle of the ball. r defines the radius of the gradient.
                <defs>
                    <radialGradient id="ballGradient" cx="50%" cy="50%" r="80%" fx="10%" fy="50%">

                    </radialGradient>
                </defs>


Now, radial gradients need stops. Stops are the points in the gradient where the color r opacity changes. For the first stop, let's define the offset attribute at 10%, meaning that when the gradient reaches 10% of its entire range, the color is bright orange.
                <defs>
                    <radialGradient id="ballGradient" cx="50%" cy="50%" r="80%" fx="10%" fy="50%">
                        <stop offset="10%" style="stop-color:rgb(255, 200, 100); stop-opacity:1" />
                    </radialGradient>
                </defs>


Then at 100%, the color should have changed to a darker shade of orange.
                <defs>
                    <radialGradient id="ballGradient" cx="50%" cy="50%" r="80%" fx="10%" fy="50%">
                        <stop offset="10%" style="stop-color:rgb(255, 200, 100); stop-opacity:1" />
                        <stop offset="100%" style="stop-color:rgb(255, 50, 0); stop-opacity:1" />
                    </radialGradient>
                </defs>


All good? Fantastic.


Let's add an animation to this decorative ball. Here, we'll animate the width of the outline. Fill in whatever values you like. Get creative!
                <circle cx="270" cy="150" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>


You'll see the decorative orange ball animate with a radiant glow effect.


Nice, right? So just place several more of these babies all  over the tree, with random cx and cy attributes, radii and animation values. In particular, try varying the animation durations.
                <circle cx="270" cy="150" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="240" cy="290" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="150" cy="330" r="7" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="290" cy="250" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="220" cy="180" r="6" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="1.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="170" cy="260" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="1.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="280" cy="320" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="230" cy="380" r="4" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="350" cy="360" r="7" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="220" cy="230" r="8" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="330" cy="290" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="240" cy="130" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>
                SVG not supported


This is great, ain't it?


Some text

Let's put up a text greeting in your SVG. It can be something boring, like "Merry Christmas". Here's two lines of text using the text tag. We position the first line on top of the tree, and the second line below.
                <defs>
                    <radialGradient id="ballGradient" cx="50%" cy="50%" r="80%" fx="10%" fy="50%">
                        <stop offset="10%" style="stop-color:rgb(255, 200, 100); stop-opacity:1" />
                        <stop offset="100%" style="stop-color:rgb(255, 50, 0); stop-opacity:1" />
                    </radialGradient>
                </defs>

                <text x="150" y="75">MERRY</text>
                <text x="80" y="455">CHRISTMAS</text>

                <circle cx="250" cy="100" r="5" class="toplight">
                    <animate attributeName="r" from="5" to="6" dur="0.1s" repeatCount="indefinite" />
                </circle>


Then let's style this. I'm going to set the font style and size, and give it a red fill and white outline. Pretty Christmassy, eh?
            .toplight
            {
                stroke: rgba(255, 255, 200, 0.3);
                stroke-width: 15;
                fill: rgba(255, 255, 200, 0.8);
            }

            text
            {
                stroke: rgba(255, 255, 255, 1);
                stroke-width: 1;
                fill: rgba(255, 0, 0, 1);
                font: bold 50px georgia;
            }


Bueno!


Next, we'll try to position this SVG in the middle of the screen. Remember, SVGs can't be directly manipulated to be relatively positioned, so let's encase this entire thing within a div. Style it using the svgContainer class.
        <div id="svgContainer">
            <svg>
                <defs>
                    <radialGradient id="ballGradient" cx="50%" cy="50%" r="80%" fx="10%" fy="50%">
                        <stop offset="10%" style="stop-color:rgb(255, 200, 100); stop-opacity:1" />
                        <stop offset="100%" style="stop-color:rgb(255, 50, 0); stop-opacity:1" />
                    </radialGradient>
                </defs>

                <text x="150" y="75">MERRY</text>
                <text x="80" y="455">CHRISTMAS</text>

                <circle cx="250" cy="100" r="5" class="toplight">
                    <animate attributeName="r" from="5" to="6" dur="0.1s" repeatCount="indefinite" />
                </circle>

                <path d="
                M 250 100
                q 0 10 -30 30 l 10 0
                q 0 10 -30 30 l 10 0
                q 0 20 -30 40 l 10 0
                q 0 20 -40 50 l 10 0
                q 0 30 -40 70 l 10 0
                q 0 40 -40 80 l 320 0
                q -40 -40 -40 -80 l 10 0
                q -40 -30 -40 -70 l 10 0 
                q -30 -20 -40 -50 l 10 0
                q -20 -10 -30 -40 l 10 0
                q -20 -10 -30 -30 l 10 0
                q -20 -10 -30 -30
                " class="tree"/>

                <circle cx="270" cy="150" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="240" cy="290" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="150" cy="330" r="7" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="290" cy="250" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="220" cy="180" r="6" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="1.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="170" cy="260" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="1.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="280" cy="320" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="230" cy="380" r="4" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="350" cy="360" r="7" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="220" cy="230" r="8" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2.5s" repeatCount="indefinite" />
                </circle>

                <circle cx="330" cy="290" r="5" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>

                <circle cx="240" cy="130" r="3" class="ball">
                    <animate attributeName="stroke-width" from="1" to="10" dur="2s" repeatCount="indefinite" />
                </circle>
                SVG not supported
            </svg>
        </div>


Then write the CSS style. While you're at it, remove the red outline of the SVG.
            body
            {
                background-color: rgba(0, 0, 50, 1);
            }

            #svgContainer
            {
                width: 500px;
                margin: 5em auto 0 auto;
            }

            svg
            {
                width: 500px;
                height: 500px;
                outline: 0px solid #FF0000;
            }


And here your SVG is nicely positioned in the middle of your screen!


Here's a preview of the actual thing...

MERRY CHRISTMAS SVG not supported


Final thoughts

SVGs are fun to write, though it would be foolhardy to totally do without CSS. Maybe some day we'll take a more in-depth look at the different approaches, but for now, it's time to enjoy your holiday season!

Here's to a well-lit Christmas!
T___T

Sunday 15 December 2019

Ways of Using Cascading Style Sheets (Part 3/3)

This is where it gets hairy. What I'm about to show you is frowned on by most professionals... in public, anyway. But it's important that you know this implementation because it does have its uses despite its several disadvantages. Just don't go crazy with it.

Inline Styling

This is where the style is implemented within the HTML tag itself, as opposed to being in a style tag in the head tag of a page.


In code, it looks like this.

index.html
<!DOCTYPE html>
<html>
    <head>
       
    </head>

    <body>
        <p style="color: #FFAA00;">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>
    </body>
</html>


Pros

It's really quick, and it overrides both External Style Sheets and Internal Style Sheets. When you want to be guaranteed that a style will be applied regardless of what other rules may have been implemented, this is your guy.

Cons

When overused, it bloats the HTML, causing it to be hard to maintain and load slower.

The example below shows multiple tags styled this way in one page. That's painful enough on its own. When you have to maintain multiple pages of this, the pain increases exponentially.

index_nightmare.html
<!DOCTYPE html>
<html>
    <head>
       
    </head>

    <body>
        <p style="color: #FFAA00;">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>

        <p style="color: #FFAA00;">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>

        <p style="color: #FFAA00;">
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>
    </body>
</html>


Use Cases

Useful when you don't have access to the existing External Style Sheet.

When the page you're writing is a quick, throwaway hack which you will never touch again or acknowledge in any way.

If you want things done quickly without thought to future maintenance, i.e, under some kind of insane deadline.

If you're some kind of masochist.

If you're not the poor bastard who is going to be maintaining these pages.

Final Notes

CSS is an indelible part of front-end web development today, and while its inclusion is something of a given, its implementation is the next most important factor. Properly implemented CSS will require a bit more effort up-front, but the maintenance benefits are worth it.

It's also a valuable way to separate style from markup (unless for some inexplicable reason you insist on using Inline Styling) and in a tech world where Separation of Concerns is something of an industry standard, any developer would do well to take heed.

Signing off in style,
T___T

Friday 13 December 2019

Ways of Using Cascading Style Sheets (Part 2/3)

There are times you want to tailor a certain look and feel for a certain HTML page only, and exclude the other pages in the site. Clever use of External Style Sheets can still accomplish that, though this may take more effort, and both the External Style Sheet and the HTML file may need to be modified.

Internal Style Sheets

These is represented by the style tag nested within the head tag of a HTML page. It can override whatever styling is dictated by an External Style Sheet provided it's declared after the reference link to that stylesheet.


In code, it looks like this.

index.html
<!DOCTYPE html>
<html>
    <head>
        <style>
            p
            {
                color: #FFAA00;
            }
        </style>
    </head>

    <body>
        <p>
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>
    </body>
</html>


If you want to use an Internal Style Sheet to override the External Style Sheet, you'd do this. In this example, you want to turn the paragraphs grey instead of orange.



styles.css
p
{
    color: #FFAA00;
}


index_grey.html
<!DOCTYPE html>
<html>
    <head>
        <link rel="stylesheet" type="text/css" href="styles.css">

        <style>
            p
            {
                color: #DDDDDD;
            }
        </style>
    </head>

    <body>
        <p>
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>
    </body>
</html>


Pros

It's a quick fix, and still separates HTML from the CSS. You can screw up the CSS or the HTML without affecting the other... mostly. A good middle ground between External Style Sheets and Inline Styling (which we will examine in the next part).

Cons

Since the CSS is bundled in with the HTML in a single file, causing that file to be larger, loading time would be affected.

If you have a bunch of these pages that you want to affect using the same change, maintenance increasingly becomes a chore as more pages are added.

Use Cases

Useful when you don't have access to the existing External Style Sheet.

Best for projects where only one HTML file is required otherwise. And also if the HTML and/or styling is light.

Used in conjunction with an External Style Sheet when there are multiple pages and some pages need their own unique styling.


Incidentally, this is the implementation I use the most when I'm making really small projects, after which I'm confident that I will never or rarely need to revisit it.

Next

Inline Styling

Tuesday 10 December 2019

Ways of Using Cascading Style Sheets (Part 1/3)

When implementing Cascading Style Sheets (CSS), there are three main ways to go about it. Each of these ways has its pros and cons (some more than others) and their own set of use cases.

Let's say, for example, that we want to turn all paragraphs orange (actually no, I really can't think of a reason why you'd want to do that unless you're color-blind, but this is just an example.) and we're going to implement that in CSS.

External Style Sheets

This is the de facto standard; if in doubt as to whether you should use an external style sheet or not, just do it. You'll probably thank yourself later.

In this implementation, your HTML and CSS are in two different files, separate and distinct. Your HTML contains a reference link to the CSS file, either over the web or in your own server.


In code, it looks like this.

styles.css
p
{
    color: #FFAA00;
}


index.html
<!DOCTYPE html>
<html>
    <head>
        <link rel="stylesheet" type="text/css" href="styles.css">
    </head>

    <body>
        <p>
            Lorem ipsum dolor sit amet, consectetur adipiscing elit. Curabitur posuere elementum ex. Duis id dolor ex. Praesent augue nulla, consectetur quis lectus eget, luctus pulvinar risus. Nunc ipsum lorem, gravida non purus ac, dapibus facilisis urna. Curabitur vel tempor erat. Maecenas egestas sapien nulla, a lobortis felis posuere ut. Ut ornare laoreet tristique.
        </p>
    </body>
</html>


Pros

Website expansion is easier. All you realistically have to do is add more pages with the same CSS reference link.

Generally, the more pages you have using one stylesheet, the greater the benefit of the External Style Sheets implementation. If you wanted to turn the paragraphs to a less glaring deep grey, all you would have to do is amend one stylesheet, and all pages referencing that stylesheet would have their paragraphs turned grey.

Great for maintenance. Because the stylesheet is in a separate file from the HTML, it's less probable that you will need to edit the HTML file itself, which can be messy. Also, this lends itself to better collaboration. Imagine there's a team maintaining the site. One is the copywriter who needs to update the text, and the other is the designer. If the style and content are in separate files, the designer and the copywriter can edit the stylesheet and the HTML respectively, concurrently.

Due to caching, the CSS file only needs to be loaded once for it to work. The HTML pages, without CSS, will load faster on their own.

Cons

Could be overkill if you're definitely only going to make one small page or two.

Use Cases

Using one stylesheet to style multiple pages. In fact, as long as you have multiple pages you want to maintain, chances are that even if you end up utilizing other CSS implementations, you will use External Style Sheets as a base implementation.


When either or both the styles and the HTML content are extremely long, it's also a good idea to keep them separate. Because the annoying thing about styles is that they can break if you miss out an opening or closing symbol. Same for HTML. You really don't want to risk screwing up your HTML or CSS due to constant (and unnecessary) edits. Sure, it's easily fixed. It's also a pain in the ass.

Next

Let's explore Internal Style Sheets.