Skip to content

Instantly share code, notes, and snippets.

@Jimmy-Z
Created March 23, 2016 12:33
Show Gist options
  • Save Jimmy-Z/921bb2648126730e0478 to your computer and use it in GitHub Desktop.
Save Jimmy-Z/921bb2648126730e0478 to your computer and use it in GitHub Desktop.
a node.js script to help you make more use of Windows 10 Spotlight lock screen images
/*
* a node.js script to help you make more use of Windows 10 Spotlight lock
* screen images.
*
* Usage:
* node spotlight-export.js <stage dir> <export dir>
*
* What it does:
* ---
* any image in spotlight dir but not in stage dir will be copied to stage dir
* any image in stage dir but not in spotlight dir will be moved to export dir
*
* so after the first run:
* if nothing new, no actions are taken.
* if anything new, it will be copied to stage dir
* if anything disappeared from spotlight dir, the corresponding file in
* stage dir will be moved to export dir
*
* it's designed to run as a scheduled task, you can then set up Windows to use
* stage dir as desktop background dir, and periodically check export dir to see
* if you want to archive them or trash them
*
* DO NOT manually move files in the stage dir, it will be copied over again by
* the next time the scheduled task is ran.
*
* Why using node:
* ---
* I tried to use WSH instead of node, unfortunately WSH doesn't support reading
* binary files, so node it is.
* simply copy files over a paticular size as jpeg won't work, there're some gif
* files above 512K.
*/
const path = require("path");
const fs = require("fs");
// I don't think png/gif files I found there are wallpapers
const FILE_TYPES = ["jpg"];
// and there are small jpg files not suitable for background, looks like app icons
const MIN_SIZE = 128 * 1024;
function chk_bytes(f, size, chks){
return chks.every(function(c){
var offset = c[0];
var len = c[1];
var b0 = c[2];
var b1 = new Buffer(len);
fs.readSync(f, b1, 0, len, offset >= 0 ? offset : size + offset);
return Buffer.compare(b0, b1) == 0;
});
}
// https://en.wikipedia.org/wiki/JPEG_File_Interchange_Format#File_format_structure
// https://en.wikipedia.org/wiki/JPEG_File_Interchange_Format#Compatibility
// https://en.wikipedia.org/wiki/Exchangeable_image_file_format
const JPEG_CHKS = [[0, 3, new Buffer("ffd8ff", "hex")], [-2, 2, new Buffer("ffd9", "hex")]];
// https://en.wikipedia.org/wiki/Portable_Network_Graphics#File_header
const PNG_CHKS = [[0, 8, new Buffer("89504e470d0a1a0a", "hex")]];
// https://en.wikipedia.org/wiki/GIF#File_format
const GIF87_CHKS = [[0, 6, new Buffer("GIF87a", "utf8")]];
const GIF89_CHKS = [[0, 6, new Buffer("GIF89a", "utf8")]];
const XML_CHKS = [[0, 5, new Buffer("<?xml", "utf8")]];
function get_file_type(f, s){
if(chk_bytes(f, s, JPEG_CHKS)){
return "jpg";
}else if(chk_bytes(f, s, PNG_CHKS)){
return "png";
}else if(chk_bytes(f, s, GIF87_CHKS)||chk_bytes(f, s, GIF89_CHKS)){
return "gif";
}else if(chk_bytes(f, s, XML_CHKS)){
return "xml";
}else{
return null;
}
}
function cp(src, dst){
fs.createReadStream(src).pipe(fs.createWriteStream(dst));
}
function spotlight_export(spotlight_path, stage_path, export_path){
var list_src = [], list_src_wtype = [];
fs.readdirSync(spotlight_path).forEach(function(n){
var p = path.join(spotlight_path, n);
var f = fs.openSync(p, "r");
var s = fs.fstatSync(f);
if(s.isFile()){
var ft = get_file_type(f, s.size);
if(ft != null){
if(FILE_TYPES.indexOf(ft) != -1 && s.size >= MIN_SIZE){
list_src.push(n);
list_src_wtype.push(n + "." + ft);
}
}else{
console.error("unknown file type:", n);
}
}
fs.closeSync(f);
});
var list_stage = fs.readdirSync(stage_path).filter(function(n){
var p = path.join(stage_path, n);
if(!fs.statSync(p).isFile()){
return false;
}
// windows might shit things like "desktop.ini"/"thumbs.db" here
return FILE_TYPES.indexOf(path.extname(n)) != -1;
});
list_src_wtype.forEach(function(n, i){
if(list_stage.indexOf(n) == -1){
console.error("copy to stage: " + n);
cp(path.join(spotlight_path, list_src[i]), path.join(stage_path, n));
}
});
list_stage.forEach(function(n){
if(list_src_wtype.indexOf(n) == -1){
console.error("move to export: " + n);
fs.renameSync(path.join(stage_path, n), path.join(export_path, n));
}
});
}
if(process.argv.length == 4){
var spotlight_path = path.join(process.env["LOCALAPPDATA"],
"\\Packages\\Microsoft.Windows.ContentDeliveryManager_cw5n1h2txyewy\\LocalState\\Assets");
var stage_path = process.argv[2];
var export_path = process.argv[3];
spotlight_export(spotlight_path, stage_path, export_path);
}else{
console.error("example:\n\tnode spotlight-export.js \"D:\Pictures\Spotlight stage\" \"D:\Pictures\Spotlight export\"");
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment