Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

webp script #151

Open
wants to merge 5 commits into
base: main
Choose a base branch
from
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
The table of contents is too big for display.
Diff view
Diff view
  •  
  •  
  •  
8 changes: 6 additions & 2 deletions .devcontainer/Dockerfile
Original file line number Diff line number Diff line change
Expand Up @@ -5,12 +5,16 @@ ARG VARIANT="14-buster"
FROM mcr.microsoft.com/vscode/devcontainers/typescript-node:0-${VARIANT}

# [Optional] Uncomment this section to install additional OS packages.
# RUN apt-get update && export DEBIAN_FRONTEND=noninteractive \
# && apt-get -y install --no-install-recommends <your-package-list-here>
RUN apt-get update && export DEBIAN_FRONTEND=noninteractive \
&& apt-get -y install --no-install-recommends webp

# [Optional] Uncomment if you want to install an additional version of node using nvm
# ARG EXTRA_NODE_VERSION=10
# RUN su node -c "source /usr/local/share/nvm/nvm.sh && nvm install ${EXTRA_NODE_VERSION}"

# [Optional] Uncomment if you want to install more global node packages
# RUN su node -c "npm install -g <your-package-list -here>"

# cwebp title-image.png -lossless -m 6 -q 100 -o title-image.webp
# find . -name '*' -exec file {} \; | grep -o -P '^.+: \w+ image' | cut -d':' -f1 | xargs -I % sh -c 'echo %; echo %.webp'
# find . -name '*' -exec file {} \; | grep -o -P '^.+: \w+ image' | cut -d':' -f1 | xargs -I % sh -c 'cwebp % -lossless -m 6 -q 100 -o %.webp'
12 changes: 6 additions & 6 deletions .devcontainer/devcontainer.json
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
// For format details, see https://aka.ms/devcontainer.json. For config options, see the README at:
// https://github.com/microsoft/vscode-dev-containers/tree/v0.163.1/containers/typescript-node
{
"name": "Node.js & TypeScript",
"name": "blog.johnnyreilly.com",
"build": {
"dockerfile": "Dockerfile",
// Update 'VARIANT' to pick a Node version: 10, 12, 14
Expand All @@ -21,12 +21,12 @@
// Use 'forwardPorts' to make a list of ports inside the container available locally.
// "forwardPorts": [],

"mounts": [
"source=blog-website-node_modules,target=${containerWorkspaceFolder}/blog-website/node_modules,type=volume",
"source=blog-website-docusaurus,target=${containerWorkspaceFolder}/blog-website/.docusaurus,type=volume"
],
// "mounts": [
// "source=blog-website-node_modules,target=${containerWorkspaceFolder}/blog-website/node_modules,type=volume",
// "source=blog-website-docusaurus,target=${containerWorkspaceFolder}/blog-website/.docusaurus,type=volume"
// ],

"postCreateCommand": "sudo chown -R node ${containerWorkspaceFolder}",
// "postCreateCommand": "sudo chown -R node ${containerWorkspaceFolder}",

// Comment out connect as root instead. More info: https://aka.ms/vscode-remote/containers/non-root.
"remoteUser": "node"
Expand Down
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
Expand Up @@ -16,9 +16,9 @@ tags:
hide_table_of_contents: false
---

The year was 2010 (not really that long ago I know) and the project that I was working on was sorely in need of a new grid component. It was an [ASP.NET WebForms](http://www.asp.net/web-forms) project and for some time we'd been using what was essentially a glorified [datagrid](http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.datagrid.aspx) which had a few extra features implemented to allow us to change column order / columns displayed / copy contents to clipboard etc. Our grid worked perfectly fine - it gave us the functionality we needed. However, it looked pretty terrible, and had some "quirky" approaches in place for supporting IE and Firefox side by side. Also, at the time we were attempting to make our app seem new and exciting again for the users. The surprising truth is that users seem to be more impressed with a visual revamp than with new or amended functionality. So I was looking for something which would make them sit up and say "oooh - isn't it pretty!". Unfortunately the nature of the organisation I was working for was not one that lended itself to paying for components. They were occasionally willing to do that but the hoops that would have to be jumped through first, the forms that would need to be signed in triplicate by people that had nearly nothing to do with the project made that an unattractive prospect. So I began my search initially looking at the various open source offerings that were around. As a minimum I was looking for something that would do what our home-grown component did already (change column order / columns displayed / copy contents to clipboard etc) but hopefully in a "nicer" way. Also, I had long been unhappy with the fact that to get our current grid to render results we did a \***full postback**\* to the server and re-rendered the whole page. Pointless! Why should you need to do all this each time when you only wanted to refresh the data? Instead I was thinking about using an [Ajax](http://en.wikipedia.org/wiki/Ajax_%28programming%29) approach; a grid that could just get the data that it needed and render it to the client. This seemed to me a vastly "cleaner" solution - why update a whole screen when you only want to update a small part of it? Why not save yourself the trouble of having to ensure that all other screen controls are persisted just as you'd like them after the postback? I also thought it was probably something that would scale better as it would massively reduce the amount of data moving backwards and forwards between client and server. No need for a full page life cycle on the server each time the grid refreshes. Just simple data travelling down the pipes of web. With the above criteria in mind I set out on my Google quest for a grid. Quite soon I found that there was a component out there which seemed to do all that I wanted and far more besides. It was called [jqGrid](http://www.trirand.com/blog/): ![](jqgrid%2Bin%2Ball%2Bits%2Bglory.png)
The year was 2010 (not really that long ago I know) and the project that I was working on was sorely in need of a new grid component. It was an [ASP.NET WebForms](http://www.asp.net/web-forms) project and for some time we'd been using what was essentially a glorified [datagrid](http://msdn.microsoft.com/en-us/library/system.web.ui.webcontrols.datagrid.aspx) which had a few extra features implemented to allow us to change column order / columns displayed / copy contents to clipboard etc. Our grid worked perfectly fine - it gave us the functionality we needed. However, it looked pretty terrible, and had some "quirky" approaches in place for supporting IE and Firefox side by side. Also, at the time we were attempting to make our app seem new and exciting again for the users. The surprising truth is that users seem to be more impressed with a visual revamp than with new or amended functionality. So I was looking for something which would make them sit up and say "oooh - isn't it pretty!". Unfortunately the nature of the organisation I was working for was not one that lended itself to paying for components. They were occasionally willing to do that but the hoops that would have to be jumped through first, the forms that would need to be signed in triplicate by people that had nearly nothing to do with the project made that an unattractive prospect. So I began my search initially looking at the various open source offerings that were around. As a minimum I was looking for something that would do what our home-grown component did already (change column order / columns displayed / copy contents to clipboard etc) but hopefully in a "nicer" way. Also, I had long been unhappy with the fact that to get our current grid to render results we did a \***full postback**\* to the server and re-rendered the whole page. Pointless! Why should you need to do all this each time when you only wanted to refresh the data? Instead I was thinking about using an [Ajax](http://en.wikipedia.org/wiki/Ajax_%28programming%29) approach; a grid that could just get the data that it needed and render it to the client. This seemed to me a vastly "cleaner" solution - why update a whole screen when you only want to update a small part of it? Why not save yourself the trouble of having to ensure that all other screen controls are persisted just as you'd like them after the postback? I also thought it was probably something that would scale better as it would massively reduce the amount of data moving backwards and forwards between client and server. No need for a full page life cycle on the server each time the grid refreshes. Just simple data travelling down the pipes of web. With the above criteria in mind I set out on my Google quest for a grid. Quite soon I found that there was a component out there which seemed to do all that I wanted and far more besides. It was called [jqGrid](http://www.trirand.com/blog/): ![](jqgrid%2Bin%2Ball%2Bits%2Bglory.webp)

Oooh look at the goodness! It had both column re-ordering and column choosing built in!: This was a \***very promising sign**\*! Now it's time for me to demonstrate my ignorance. According to the website this grid component was a "jQuery plugin". At the time I read this I had no idea what jQuery was at all - let alone what a plugin for it was. Anyway, I don't want to get diverted so let's just say that reading this lead to me getting an urgent education about some of the client side aspects of the modern web that I had been previously unaware of. I digress. This component did exactly what I wanted in terms of just sending data down the pipe. jqGrid worked with a whole number of possible data sources; XML, Array but the most exciting for me was obviously [JSON](http://www.json.org/). Take a look a the grid rendered below and the JSON that powered it (all from a simple [GET](http://www.trirand.com/blog/jqgrid/server.php?q=2&_search=false&nd=1326531357333&rows=10&page=1&sidx=id&sord=desc) request): ![](Check%2Bout%2Bthe%2BJSON.png)
Oooh look at the goodness! It had both column re-ordering and column choosing built in!: This was a \***very promising sign**\*! Now it's time for me to demonstrate my ignorance. According to the website this grid component was a "jQuery plugin". At the time I read this I had no idea what jQuery was at all - let alone what a plugin for it was. Anyway, I don't want to get diverted so let's just say that reading this lead to me getting an urgent education about some of the client side aspects of the modern web that I had been previously unaware of. I digress. This component did exactly what I wanted in terms of just sending data down the pipe. jqGrid worked with a whole number of possible data sources; XML, Array but the most exciting for me was obviously [JSON](http://www.json.org/). Take a look a the grid rendered below and the JSON that powered it (all from a simple [GET](http://www.trirand.com/blog/jqgrid/server.php?q=2&_search=false&nd=1326531357333&rows=10&page=1&sidx=id&sord=desc) request): ![](Check%2Bout%2Bthe%2BJSON.webp)

As you can see from the above screenshot, the grid has populated itself using the results of a web request. The only information that has gone to the server are the relevant criteria to drive the search results. The only information that has come back from the server is the data needed to drive the grid. Simple. Beautiful. I loved it and I wanted to use it. So I did! I had to take a few steps that most people thinking about using a grid component probably wont need to. First of all I had to write an ASP.Net WebForms wrapper for jqGrid which could be implemented in a similar way to our current custom datagrid. This was because, until the users were convinced that the new grid was better than the old both had to co-exist in the project and the user would have the option to switch between the two. This WebForms wrapper plugged into our old school XML column definition files and translated them into JSON for the grid. It also took [datasets](http://msdn.microsoft.com/en-us/library/system.data.dataset.aspx) (which drove our old grid) and translated them into jqGrid-friendly JSON. I wanted to power the jqGrid using WebMethods on ASPX's. After a little digging I found [Dave Ward of Encosia's post](http://encosia.com/using-jquery-to-directly-call-aspnet-ajax-page-methods/) which made it very simple (and in line with this I switched over from [GET](http://en.wikipedia.org/wiki/GET_%28HTTP%29#Request_methods) requests to [POSTs](http://en.wikipedia.org/wiki/POST_%28HTTP%29)). Finally I wrote some custom javascript which added a button to jqGrid which, if clicked, would copy the contents of the jqGrid to the clipboard (this was the only bit of functionality that didn't appear to be implemented out of the box with jqGrid). I think I'm going to leave it there for now but I just wanted to say that I think jqGrid is a fantastic component and it's certainly made my life better! It's: - well supported, there is lots on [StackOverflow](http://stackoverflow.com/questions/tagged/jqgrid) and the like about it

Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
2 changes: 1 addition & 1 deletion blog-website/blog/2012-02-23-joy-of-json/index.md
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ var anotherCarMadeFromMyJSON = JSON.parse(myCarJSON);
//anotherCarMadeFromMyJSON will be a brand new "car" object
```

I've also demonstrated this using the Chrome Console: ![](Using%2BJSON.png)
I've also demonstrated this using the Chrome Console: ![](Using%2BJSON.webp)

Crockford initially invented/discovered JSON himself and wrote a little helper library which provided a JSON object to be used by all and sundry. This can be found here: [JSON on GitHub](https://github.com/douglascrockford/JSON-js) Because JSON was so clearly wonderful, glorious and useful it ended up becoming a part of the EcmaScript 5 spec (in fact it's worth reading the brilliant [John Resig's blog post](http://ejohn.org/blog/ecmascript-5-strict-mode-json-and-more/) on this). This has lead to JSON being offered [natively in browsers](http://en.wikipedia.org/wiki/JSON#Native_encoding_and_decoding_in_browsers) for quite some time. However, for those of us (and I am one alas) still supporting IE 6 and the like we still have Crockfords JSON2.js to fall back on.

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -176,7 +176,7 @@ attribute for an input if you wish it to be evaluated with unobtrusive validatio

Validation in action:

![](validation-screenshot2.png)
![](validation-screenshot2.webp)

Well I've gone on for far too long but I am happy to have an approach that does what I need. It does feel like a slightly hacky solution and I expect that there is a better approach for this that I'm not aware of. As much as anything else I've written this post in the hope that someone who knows this better approach will set me straight. In summary, this works. But if you're aware of a better solution then please do get in contact - I'd love to know!

Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ hide_table_of_contents: false

The speed of change makes fools of us all. Since I originally wrote this post all of 3 weeks ago Visual Studio 11 beta has been released and the issues I was seeking to solve have pretty much been resolved by the new innovations found therein. It's nicely detailed in [@carlbergenhem](http://www.twitter.com/carlbergenhem)'s blog post: [My Top 5 Visual Studio 11 Designer Improvements for ASP.NET 4.5 Development](https://blogs.telerik.com/blogs/posts/12-03-26/my-top-5-visual-studio-11-designer-improvements-for-asp-net-4-5-development.aspx). I've left the post in place below but much of what I said (particularly with regard to Hungarian Notation) I've now moved away from. That was originally my intention anyway so that's no bad thing. The one HN artefact that I've held onto is using "$" as a prefix for jQuery objects. I think that still makes sense. I would have written my first line of JavaScript in probably 2000. It probably looked something like this: `alert('hello world')`. I know. Classy. As I've mentioned before it was around 2010 before I took JavaScript in any way seriously. Certainly it was then when I started to actively learn the language. Because up until this point I'd been studiously avoiding writing any JavaScript at all I'd never really given thought to forms and conventions. When I wrote any JavaScript I just used the same style and approaches as I used in my main development language (of C#). By and large I have been following the .net naming conventions which are ably explained by Pete Brown [here](http://10rem.net/articles/net-naming-conventions-and-programming-standards---best-practices). Over time I have started to move away from this approach. Without a deliberate intention to do so I have found myself adopting a different style for my JavaScript code as compared with anything else I write. I wouldn't go so far as to say I'm completely happy with the style I'm currently using. But I find it more helpful than not and thought it might be worth talking about. It was really 2 things that started me down the road of "rolling my own" convention: dynamic typing and the lack of safety nets. Let's take each in turn.... ### 1\. Dynamic typing

Having grown up (in a development sense) using compiled and strongly-typed languages I was used to the IDE making it pretty clear what was what through friendly tooltips and the like: ![](IDE.png)
Having grown up (in a development sense) using compiled and strongly-typed languages I was used to the IDE making it pretty clear what was what through friendly tooltips and the like: ![](IDE.webp)

JavaScript is loosely / dynamically typed ([occasionally called "untyped" but let's not go there](http://stackoverflow.com/questions/9154388/does-untyped-also-mean-dynamically-typed-in-the-academic-cs-world)). This means that the IDE can't easily determine what's what. So no tooltips for you sunshine. ### 2\. The lack of safety nets / running with scissors

Expand Down Expand Up @@ -40,7 +40,7 @@ console.log(iAmANumber); //Logs a function
iAmANumber('I am not a number, I am a free man!'); //Calls a function which performs a log
```

Now if I were to attempt something similar in C# fuggedaboudit but JavaScript; no I'm romping home free: ![](Mad%2BStuff.png)
Now if I were to attempt something similar in C# fuggedaboudit but JavaScript; no I'm romping home free: ![](Mad%2BStuff.webp)

Now I'm not saying that you should ever do the above, and thinking about it I can't think of a situation where you'd want to (suggestions on a postcard). But the point is it's possible. And because it's possible to do this deliberately, it's doubly possible to do this accidentally. My point is this: it's easy to make bugs in JavaScript. ## What ~~Katy~~ Johnny Did Next

Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Original file line number Diff line number Diff line change
Expand Up @@ -66,7 +66,7 @@ Using the above I can create myself my very own "JohnReilly" like so:
var johnReilly = new JohnReilly();
```

And it will look like this: ![](C%2523%2Bversion%2Bof%2BJohnReilly.png)
And it will look like this: ![](C%2523%2Bversion%2Bof%2BJohnReilly.webp)

I was looking to implement something similar on the client and within JavaScript. I was keen to ensure [code reuse](http://en.wikipedia.org/wiki/Code_reuse). And my inclination to keep things simple made me wary of making use of the [prototype](http://bonsaiden.github.com/JavaScript-Garden/#object.prototype). It is undoubtedly powerful but I don't think even the mighty [Crockford](http://javascript.crockford.com/prototypal.html) would consider it "simple". Also I had the reservation of exposing my object to the global scope. So what to do? I had an idea.... ## The Big Idea

Expand Down Expand Up @@ -114,7 +114,7 @@ $.publish('PubSub.Inheritance.Emulation', [oJohnReilly]); //Empty object "publis
console.log(JSON.stringify(oJohnReilly)); //Show me this thing you call "JohnReilly"
```

And it will look like this: ![](JavaScript%2Bversion%2Bof%2BJohnReilly.png)
And it will look like this: ![](JavaScript%2Bversion%2Bof%2BJohnReilly.webp)

And it works. Obviously the example I've given above it somewhat naive - in reality my object properties are driven by GUI components rather than hard-coded. But I hope this illustrates the point. This technique allows you to simply share functionality between different JavaScript files and so keep your codebase tight. I certainly wouldn't recommend it for all circumstances but when you're doing something as simple as building up an object to be used to pass data around (as I am) then it works very well indeed. ## A Final Thought on Script Ordering

Expand Down
Binary file not shown.
Binary file not shown.
Binary file not shown.
Binary file not shown.
Loading