[{"data":1,"prerenderedAt":2531},["ShallowReactive",2],{"notes-to-self-slugs":3,"posts":364,"post-mystery-theater":1657},[4,7,10,13,16,19,22,25,28,31,34,37,40,43,46,49,52,55,58,61,64,67,70,73,76,79,82,85,88,91,94,97,100,103,106,109,112,115,118,121,124,127,130,133,136,139,142,145,148,151,154,157,160,163,166,169,172,175,178,181,184,187,190,193,196,199,202,205,208,211,214,217,220,223,226,229,232,235,238,241,244,247,250,253,256,259,262,265,268,271,274,277,280,283,286,289,292,295,298,301,304,307,310,313,316,319,322,325,328,331,334,337,340,343,346,349,352,355,358,361],{"title":5,"slug":6},"3D Math/Graphics","3d-mathgraphics",{"title":8,"slug":9},"3d modeling tools and resources","3d-modeling-tools-and-resources",{"title":11,"slug":12},"3D Printing","3d-printing",{"title":14,"slug":15},"A Mathematical Expression Parser in TypeScript","a-mathematical-expression-parser-in-typescript",{"title":17,"slug":18},"Ad Hoc","ad-hoc",{"title":20,"slug":21},"AI: ChatGPT and the Nature of Intelligence","ai-chatgpt-and-the-nature-of-intelligence",{"title":23,"slug":24},"Apple ][ Stuff","apple-stuff",{"title":26,"slug":27},"Art You Like","art-you-like",{"title":29,"slug":30},"Artists","artists",{"title":32,"slug":33},"Big O (AKA Big Oh) notation","big-o-aka-big-oh-notation",{"title":35,"slug":36},"Big O Cheat Sheet","big-o-cheat-sheet",{"title":38,"slug":39},"Blender","blender",{"title":41,"slug":42},"Books about Business, Process","books-about-business-process",{"title":44,"slug":45},"Break a Concave Shape into Multiple Convex Shapes","break-a-concave-shape-into-multiple-convex-shapes",{"title":47,"slug":48},"C++","c",{"title":50,"slug":51},"C Template Library","c-template-library",{"title":53,"slug":54},"CMS","cms",{"title":56,"slug":57},"Color Tools","color-tools",{"title":59,"slug":60},"CSS: Flex, a Great Explanation","css-flex-a-great-explanation",{"title":62,"slug":63},"CSS - Line Height Unit","css-line-height-unit",{"title":65,"slug":66},"Data Editor","data-editor",{"title":68,"slug":69},"Data transformation tool","data-transformation-tool",{"title":71,"slug":72},"Deep Learning","deep-learning",{"title":74,"slug":75},"Do a Circle and a Line Intersect?","do-a-circle-and-a-line-intersect",{"title":77,"slug":78},"Dungeon Deep/Wicked Engine","dungeon-deepwicked-engine",{"title":80,"slug":81},"Electric Car","electric-car",{"title":83,"slug":84},"Fast Pseudo-random number generator","fast-pseudo-random-number-generator",{"title":86,"slug":87},"Fermi’s Paradox, the Drake Equation, and All That","fermis-paradox-the-drake-equation-and-all-that",{"title":89,"slug":90},"Fonts","fonts",{"title":92,"slug":93},"Frameworks and Libraries of Interest","frameworks-and-libraries-of-interest",{"title":95,"slug":96},"Game Dev","game-dev",{"title":98,"slug":99},"Game Idea - Lunar Lander + Motherload","game-idea-lunar-lander-motherload",{"title":101,"slug":102},"Git Cheat Sheet","git-cheat-sheet",{"title":104,"slug":105},"Godot Exploration","godot-exploration",{"title":107,"slug":108},"Google Apps for biggerplanet.com","google-apps-for-biggerplanetcom",{"title":110,"slug":111},"GUIs in Movies","guis-in-movies",{"title":113,"slug":114},"Guy Uses Blender for Classic 2001/Alien Greeble","guy-uses-blender-for-classic-2001alien-greeble",{"title":116,"slug":117},"HDHomerun Connect Duo","hdhomerun-connect-duo",{"title":119,"slug":120},"Heroku shutting down free tiers","heroku-shutting-down-free-tiers",{"title":122,"slug":123},"Home Improvement","home-improvement",{"title":125,"slug":126},"How to Promote Phone Game","how-to-promote-phone-game",{"title":128,"slug":129},"HTML Dialog Element","html-dialog-element",{"title":131,"slug":132},"Ice maker Repair","ice-maker-repair",{"title":134,"slug":135},"Illustrator => Affinity Designer","illustrator-affinity-designer",{"title":137,"slug":138},"Image, Picture, Visual Resources","image-picture-visual-resources",{"title":140,"slug":141},"Interactive Narrative Scripting Language","interactive-narrative-scripting-language",{"title":143,"slug":144},"Interview with Zachary Boerner, Branch Cut, TableRaven","interview-with-zachary-boerner-branch-cut-tableraven",{"title":146,"slug":147},"JavaScript crypto ","javascript-crypto",{"title":149,"slug":150},"Job search","job-search",{"title":152,"slug":153},"Jobs","jobs",{"title":155,"slug":156},"Keep macOS awake","keep-macos-awake",{"title":158,"slug":159},"Keyboards","keyboards",{"title":161,"slug":162},"Linear Interpolation (lerp)","linear-interpolation-lerp",{"title":164,"slug":165},"Lost Music","lost-music",{"title":167,"slug":168},"Making a Vue/Nuxt Module","making-a-vuenuxt-module",{"title":170,"slug":171},"Marketing","marketing",{"title":173,"slug":174},"Meta Tools","meta-tools",{"title":176,"slug":177},"Military Ranks","military-ranks",{"title":179,"slug":180},"Miscellaneous Digitized Manuscripts and Books for Source Material, Art","miscellaneous-digitized-manuscripts-and-books-for-source-material-art",{"title":182,"slug":183},"More ChatGPT","more-chatgpt",{"title":185,"slug":186},"Movies to Watch","movies-to-watch",{"title":188,"slug":189},"Music (for listening) and Movies/Shows to Watch","music-for-listening-and-moviesshows-to-watch",{"title":191,"slug":192},"Music (Learning, Playing)","music-learning-playing",{"title":194,"slug":195},"Music Resource","music-resource",{"title":197,"slug":198},"Mystery Theater","mystery-theater",{"title":200,"slug":201},"Numeric Input on Mobile","numeric-input-on-mobile",{"title":203,"slug":204},"Old Mac Emulation in Browser","old-mac-emulation-in-browser",{"title":206,"slug":207},"On \"Cancel Culture\"","on-cancel-culture",{"title":209,"slug":210},"On Optimism","on-optimism",{"title":212,"slug":213},"On Testing","on-testing",{"title":215,"slug":216},"Password/Passphrase Generator Idea","passwordpassphrase-generator-idea",{"title":218,"slug":219},"Patent Troll","patent-troll",{"title":221,"slug":222},"Plants","plants",{"title":224,"slug":225},"PlayKode Research","playkode-research",{"title":227,"slug":228},"Plots","plots",{"title":230,"slug":231},"Poetry, Inspirational ","poetry-inspirational",{"title":233,"slug":234},"Portable Screen/Monitor","portable-screenmonitor",{"title":236,"slug":237},"Procedural dungeon for rogue like","procedural-dungeon-for-rogue-like",{"title":239,"slug":240},"Products to Buy","products-to-buy",{"title":242,"slug":243},"Quest VR Floor Height Problem","quest-vr-floor-height-problem",{"title":245,"slug":246},"React","react",{"title":248,"slug":249},"Recipes/Techniques","recipestechniques",{"title":251,"slug":252},"Red Sea Navigation","red-sea-navigation",{"title":254,"slug":255},"Regex Tools","regex-tools",{"title":257,"slug":258},"Roche Brothers Wines","roche-brothers-wines",{"title":260,"slug":261},"Science to exploit and mangle for fiction","science-to-exploit-and-mangle-for-fiction",{"title":263,"slug":264},"SCP Tips","scp-tips",{"title":266,"slug":267},"SDL","sdl",{"title":269,"slug":270},"SETI Editorial: Probing for ETI's Probes in the Solar System","seti-editorial-probing-for-etis-probes-in-the-solar-system",{"title":272,"slug":273},"Setting up sublime to be like iA Writer","setting-up-sublime-to-be-like-ia-writer",{"title":275,"slug":276},"Shared Element Transition","shared-element-transition",{"title":278,"slug":279},"Simulation Hypothesis","simulation-hypothesis",{"title":281,"slug":282},"Solar","solar",{"title":284,"slug":285},"Songs to Sample","songs-to-sample",{"title":287,"slug":288},"Sound Effects","sound-effects",{"title":290,"slug":291},"SSH tips","ssh-tips",{"title":293,"slug":294},"Supabase","supabase",{"title":296,"slug":297},"SVG Tools","svg-tools",{"title":299,"slug":300},"SvS/NoS Reboot notes","svsnos-reboot-notes",{"title":302,"slug":303},"Swift Resources & Notes","swift-resources-notes",{"title":305,"slug":306},"The Original Spacewar!","the-original-spacewar",{"title":308,"slug":309},"The Snowflake Method For Designing A Novel","the-snowflake-method-for-designing-a-novel",{"title":311,"slug":312},"The Thirty-Seven Basic Dramatic Situations","the-thirty-seven-basic-dramatic-situations",{"title":314,"slug":315},"Three Magic Words","three-magic-words",{"title":317,"slug":318},"Three.js","threejs",{"title":320,"slug":321},"Tools & Books","tools-books",{"title":323,"slug":324},"Vector Rendering Engine (C++)","vector-rendering-engine-c",{"title":326,"slug":327},"VR","vr",{"title":329,"slug":330},"Vue 3, Nuxt, Nuxt Content, & TypeScript","vue-3-nuxt-nuxt-content-typescript",{"title":332,"slug":333},"Vue and Vue Adjacent","vue-and-vue-adjacent",{"title":335,"slug":336},"Web dev","web-dev",{"title":338,"slug":339},"WebAssembly (WASM)/Web Worker Notes","webassembly-wasmweb-worker-notes",{"title":341,"slug":342},"WebGPU","webgpu",{"title":344,"slug":345},"What God, Quantum Mechanics and Consciousness Have in Common","what-god-quantum-mechanics-and-consciousness-have-in-common",{"title":347,"slug":348},"what’s an entity component system?","whats-an-entity-component-system",{"title":350,"slug":351},"Whisper","whisper",{"title":353,"slug":354},"Whitelist websites for kid use of raspberry pi","whitelist-websites-for-kid-use-of-raspberry-pi",{"title":356,"slug":357},"Why You Will Marry the Wrong Person","why-you-will-marry-the-wrong-person",{"title":359,"slug":360},"Word order","word-order",{"title":362,"slug":363},"You are h…","you-are-h",[365,748,925,974,1013,1035,1084,1129,1317,1596],{"_path":366,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":104,"description":369,"slug":105,"date":370,"dateString":371,"encrypted":368,"encryptedBody":372,"body":373,"_type":742,"_id":743,"_source":744,"_file":745,"_stem":746,"_extension":747},"/notes-to-self/godot-exploration","notes-to-self",false,"",1737918608542,"Shaders",null,{"type":374,"children":375,"toc":735},"root",[376,421,427,520,525,586,596,607,618,623,631,638,653,660,665,670,684,691,696,702,713,724],{"type":377,"tag":378,"props":379,"children":380},"element","ul",{},[381,388,416],{"type":377,"tag":382,"props":383,"children":384},"li",{},[385],{"type":386,"value":387},"text","Devs are committed to home-grown “GDScript”",{"type":377,"tag":382,"props":389,"children":390},{},[391,393],{"type":386,"value":392},"Swift looked promising but:\n",{"type":377,"tag":378,"props":394,"children":395},{},[396,401,406,411],{"type":377,"tag":382,"props":397,"children":398},{},[399],{"type":386,"value":400},"Multi step process for build changes (build, then copy; could be automated?)",{"type":377,"tag":382,"props":402,"children":403},{},[404],{"type":386,"value":405},"Currently sketchy x-platform support",{"type":377,"tag":382,"props":407,"children":408},{},[409],{"type":386,"value":410},"Maybe worth revisiting later",{"type":377,"tag":382,"props":412,"children":413},{},[414],{"type":386,"value":415},"SwiftGodotKit inverts the problem and seems to use Godot by embedding it, like a framework?",{"type":377,"tag":382,"props":417,"children":418},{},[419],{"type":386,"value":420},"C# is typed and structured but suffers from garbage collection stutters; appears to be the only real alternative to GDScript",{"type":377,"tag":422,"props":423,"children":424},"p",{},[425],{"type":386,"value":426},"Not Godot-flavor, but educational",{"type":377,"tag":378,"props":428,"children":429},{},[430,443,454,465,476,487,498,509],{"type":377,"tag":382,"props":431,"children":432},{},[433,441],{"type":377,"tag":434,"props":435,"children":439},"a",{"href":436,"rel":437},"https://www.shadertoy.com/view/Md23DV",[438],"nofollow",[440],{"type":386,"value":436},{"type":386,"value":442}," — tutorial",{"type":377,"tag":382,"props":444,"children":445},{},[446,452],{"type":377,"tag":434,"props":447,"children":450},{"href":448,"rel":449},"https://www.shadertoy.com/view/ltl3WS",[438],[451],{"type":386,"value":448},{"type":386,"value":453}," cloudy stars",{"type":377,"tag":382,"props":455,"children":456},{},[457,463],{"type":377,"tag":434,"props":458,"children":461},{"href":459,"rel":460},"https://www.shadertoy.com/view/Msl3WH",[438],[462],{"type":386,"value":459},{"type":386,"value":464}," warp towards viewer",{"type":377,"tag":382,"props":466,"children":467},{},[468,474],{"type":377,"tag":434,"props":469,"children":472},{"href":470,"rel":471},"https://www.shadertoy.com/view/4tjSDt",[438],[473],{"type":386,"value":470},{"type":386,"value":475}," another warp",{"type":377,"tag":382,"props":477,"children":478},{},[479,485],{"type":377,"tag":434,"props":480,"children":483},{"href":481,"rel":482},"https://www.shadertoy.com/view/lsc3z4",[438],[484],{"type":386,"value":481},{"type":386,"value":486}," other stars",{"type":377,"tag":382,"props":488,"children":489},{},[490,496],{"type":377,"tag":434,"props":491,"children":494},{"href":492,"rel":493},"https://www.shadertoy.com/view/Xd3GWn",[438],[495],{"type":386,"value":492},{"type":386,"value":497}," excellent explosion",{"type":377,"tag":382,"props":499,"children":500},{},[501,507],{"type":377,"tag":434,"props":502,"children":505},{"href":503,"rel":504},"https://www.shadertoy.com/view/Xss3DS",[438],[506],{"type":386,"value":503},{"type":386,"value":508}," inspiration",{"type":377,"tag":382,"props":510,"children":511},{},[512,518],{"type":377,"tag":434,"props":513,"children":516},{"href":514,"rel":515},"https://www.shadertoy.com/view/MdfGRX",[438],[517],{"type":386,"value":514},{"type":386,"value":519}," incredible fire clouds",{"type":377,"tag":422,"props":521,"children":522},{},[523],{"type":386,"value":524},"Additional shaders, lightning:",{"type":377,"tag":378,"props":526,"children":527},{},[528,538,548,558,568],{"type":377,"tag":382,"props":529,"children":530},{},[531],{"type":377,"tag":434,"props":532,"children":535},{"href":533,"rel":534},"https://www.shadertoy.com/view/lfySRz",[438],[536],{"type":386,"value":537},"Noise as Electricity rays",{"type":377,"tag":382,"props":539,"children":540},{},[541],{"type":377,"tag":434,"props":542,"children":545},{"href":543,"rel":544},"https://www.shadertoy.com/view/MdSGW1",[438],[546],{"type":386,"value":547},"Lightning spark",{"type":377,"tag":382,"props":549,"children":550},{},[551],{"type":377,"tag":434,"props":552,"children":555},{"href":553,"rel":554},"https://www.shadertoy.com/view/dsXfDn",[438],[556],{"type":386,"value":557},"fbm lightning",{"type":377,"tag":382,"props":559,"children":560},{},[561],{"type":377,"tag":434,"props":562,"children":565},{"href":563,"rel":564},"https://www.shadertoy.com/view/st3fRf",[438],[566],{"type":386,"value":567},"Lightning Shader (v1)",{"type":377,"tag":382,"props":569,"children":570},{},[571,578,580],{"type":377,"tag":434,"props":572,"children":575},{"href":573,"rel":574},"https://www.shadertoy.com/view/4scGWj",[438],[576],{"type":386,"value":577},"Electro",{"type":386,"value":579},"\nPlanet: needs an image? Apparently only normals (no color, e.g.) Possible to vary lighting (appears so)? ",{"type":377,"tag":434,"props":581,"children":584},{"href":582,"rel":583},"https://www.shadertoy.com/view/XsGBDt",[438],[585],{"type":386,"value":582},{"type":377,"tag":587,"props":588,"children":590},"pre",{"code":589},"#define SCALE 0.85\n\nfloat map(vec3 p) {\n    float lat = 90. - acos(p.y / length(p)) * 180./PI;\n    float lon = atan(p.x, p.z) * 180./PI;\n    vec2 uv = vec2(lon/360., lat/180.) + 0.5;\n    return texture(iChannel0, uv).x;\n}\n\nvec3 normal(vec3 p) {\n    vec2 e = vec2(1,0)/1e3;\n    p += 0.01 * vec3(\n        map(p + e.xyy) - map(p - e.xyy),\n        map(p + e.yxy) - map(p - e.yxy),\n        map(p + e.yyx) - map(p - e.yyx))/ (2. * length(e));\n    return normalize(p);\n}\n\nvoid mainImage( out vec4 fragColor, in vec2 fragCoord ) {\n    vec2 p = (2. * fragCoord.xy - iResolution.xy) / iResolution.y;\n    float lat = 15. * sin(0.1 * iTime);\n    float lon = 7.5 * iTime + 100.;\n    if (iMouse.z > 0.) {\n        lat = 90.  - 180. * iMouse.y/iResolution.y;\n        lon = 180. - 360. * iMouse.x/iResolution.x;\n    }\n    vec3 camPos = 10. * vec3(sin(lon*PI/180.) * cos(lat*PI/180.), sin(lat*PI/180.), cos(lon*PI/180.) * cos(lat*PI/180.));\n    vec3 w = normalize(-camPos);\n    vec3 u = normalize(cross(w, vec3(0,1,0)));\n    vec3 v = normalize(cross(u, w));\n    mat3 camera = mat3(u, v, w);\n    \n    vec3 dir = normalize(camera * vec3(p / SCALE, length(camPos)));\n    float dist = iSphere(camPos, dir, vec4(0,0,0,1));\n    fragColor = vec4(0);\n    if (dist > 0.) {\n        vec3 q = camPos + dir * dist;\n        float c = map(q);\n        vec3 n = normal(q);\n        float light = clamp(dot(n, normalize(vec3(-4,1,2))), 0., 1.);\n        float heat = clamp(2. / pow(iTime, 2.), 0., 1.);\n        fragColor = light * mix(vec4(0.58, 0.57, 0.55, 1), vec4(0.15, 0.13, 0.1, 1), smoothstep(0., 3., c));\n        fragColor += 5. * c * heat * vec4(1., 0.15, 0.05, 1.);\n    }\n    fragColor.rgb = mix(fragColor.rgb, vec3(0), smoothstep(SCALE - 4./iResolution.y, SCALE + 1./iResolution.y, length(p)));\n    fragColor.rgb = pow(fragColor.rgb, vec3(1./2.2));\n}\n",[591],{"type":377,"tag":592,"props":593,"children":594},"code",{"__ignoreMap":369},[595],{"type":386,"value":589},{"type":377,"tag":422,"props":597,"children":598},{},[599,601],{"type":386,"value":600},"This one has an atmosphere, moving clouds, and two stars with impressive eclipse effect: ",{"type":377,"tag":434,"props":602,"children":605},{"href":603,"rel":604},"https://www.shadertoy.com/view/XsjGRd",[438],[606],{"type":386,"value":603},{"type":377,"tag":422,"props":608,"children":609},{},[610,612],{"type":386,"value":611},"Unrelated amazing water: ",{"type":377,"tag":434,"props":613,"children":616},{"href":614,"rel":615},"https://www.shadertoy.com/view/wldBRf",[438],[617],{"type":386,"value":614},{"type":377,"tag":422,"props":619,"children":620},{},[621],{"type":386,"value":622},"Claude authored vertex shader for keeping mesh at constant size, untested:",{"type":377,"tag":587,"props":624,"children":626},{"code":625},"shader_type spatial;\nrender_mode unshaded;\n\nuniform float size_factor = 1.0;\nuniform float min_distance = 1.0;\nuniform float max_distance = 10.0;\n\nvoid vertex() {\n    // Transform the vertex to view space\n    vec4 view_pos = MODELVIEW_MATRIX * vec4(VERTEX, 1.0);\n    \n    // Calculate the distance from the camera\n    float distance = length(view_pos.xyz);\n    \n    // Clamp the distance between min and max values\n    distance = clamp(distance, min_distance, max_distance);\n    \n    // Scale the vertex based on its distance from the camera\n    VERTEX *= distance * size_factor;\n    \n    // Apply model-view-projection transformation\n    POSITION = PROJECTION_MATRIX * view_pos;\n}\n\nvoid fragment() {\n    // Set the albedo color (you can modify this or add textures as needed)\n    ALBEDO = vec3(1.0, 1.0, 1.0);\n}\n",[627],{"type":377,"tag":592,"props":628,"children":629},{"__ignoreMap":369},[630],{"type":386,"value":625},{"type":377,"tag":632,"props":633,"children":635},"h4",{"id":634},"explosions",[636],{"type":386,"value":637},"Explosions",{"type":377,"tag":378,"props":639,"children":640},{},[641,650],{"type":377,"tag":382,"props":642,"children":643},{},[644],{"type":377,"tag":434,"props":645,"children":648},{"href":646,"rel":647},"https://www.shadertoy.com/view/lcKGRc",[438],[649],{"type":386,"value":646},{"type":377,"tag":382,"props":651,"children":652},{},[],{"type":377,"tag":654,"props":655,"children":657},"h3",{"id":656},"trying-to-get-some-things-to-glow-other-things-to-not-glow",[658],{"type":386,"value":659},"Trying to get some things to glow, other things to not glow",{"type":377,"tag":422,"props":661,"children":662},{},[663],{"type":386,"value":664},"You discovered that the UI elements in your experiment (the grid in Ares) were glowing. You tried many different ways (custom shader? complicated pipeline using scary new under-documented compositing in godot?) You wanted to keep the specular highlights glowing and the “engines” glowing, but exclude the UI elements.",{"type":377,"tag":422,"props":666,"children":667},{},[668],{"type":386,"value":669},"Answer was to keep the worldenvironment glow HDR threshold at 1 (makes sense) but to:",{"type":377,"tag":671,"props":672,"children":673},"ol",{},[674,679],{"type":377,"tag":382,"props":675,"children":676},{},[677],{"type":386,"value":678},"for specular: up the “energy” of the directional light above 1 and",{"type":377,"tag":382,"props":680,"children":681},{},[682],{"type":386,"value":683},"for glowing engines: don’t know how to do it for a glow map, but for a simple emissive color (should suit our needs), in blender, set the material emission strength to a “value” and enter some high number above 1 (I assume, I used 4)",{"type":377,"tag":685,"props":686,"children":688},"h2",{"id":687},"_3rd-person",[689],{"type":386,"value":690},"3rd person",{"type":377,"tag":422,"props":692,"children":693},{},[694],{"type":386,"value":695},"Not that you’re doing it, but Google fair fight godot YouTube “",{"type":377,"tag":685,"props":697,"children":699},{"id":698},"image-to-2d-collision-shape",[700],{"type":386,"value":701},"Image to 2D Collision Shape!",{"type":377,"tag":422,"props":703,"children":704},{},[705,707],{"type":386,"value":706},"From ",{"type":377,"tag":434,"props":708,"children":711},{"href":709,"rel":710},"https://youtu.be/zeYtjYPjCkg?si=KhbpY4eVneB8EG7O&t=224",[438],[712],{"type":386,"value":709},{"type":377,"tag":587,"props":714,"children":719},{"code":715,"language":716,"meta":369,"className":717},"func SpriteToPolygon():\n  var bitmap = BitMap.new()\n  bitmap.create_from_image_alpha(\n    get_parent().get_texture().get_image()\n  )\n\n  polys = bitmap.opaque_to_polygons(\n    Rect2(\n      Vector2.ZERO,\n      get_parent().get_texture().get_size()\n    ),\n    epsilon\n  )\n\n  for poly in polys:\n    collision_polygon = CollisionPolygon2D.new()\n    collision_polygon.polygon = poly\n    add_child(collision_polygon)\n\n  if get_parent().centered:\n    collision_polygon.position -= Vector2 (bitmap.get_size() / 2)\n    collision_polygon.position += get_parent().offset\n","gdscript",[718],"language-gdscript",[720],{"type":377,"tag":592,"props":721,"children":722},{"__ignoreMap":369},[723],{"type":386,"value":715},{"type":377,"tag":422,"props":725,"children":726},{},[727,729],{"type":386,"value":728},"Random recommended extensions ",{"type":377,"tag":434,"props":730,"children":733},{"href":731,"rel":732},"https://www.reddit.com/r/godot/s/O2eVtikL0Z",[438],[734],{"type":386,"value":731},{"title":369,"searchDepth":736,"depth":736,"links":737},2,[738,740,741],{"id":656,"depth":739,"text":659},3,{"id":687,"depth":736,"text":690},{"id":698,"depth":736,"text":701},"markdown","content:notes-to-self:godot-exploration.md","content","notes-to-self/godot-exploration.md","notes-to-self/godot-exploration","md",{"_path":749,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":116,"description":750,"slug":117,"date":751,"dateString":752,"encrypted":368,"encryptedBody":372,"body":753,"_type":742,"_id":922,"_source":744,"_file":923,"_stem":924,"_extension":747},"/notes-to-self/hdhomerun-connect-duo","Does not have built-in wifi. Can only connect via ethernet. Also needs to be directly connected to antenna. Your house’s router is in the basement, terrible place for an antenna.",1735146000000,"2024-12-25",{"type":374,"children":754,"toc":919},[755,759,764,769,780,785,793,804,813,819,824,829,834,839,849,868,880,894,899,904,909,914],{"type":377,"tag":422,"props":756,"children":757},{},[758],{"type":386,"value":750},{"type":377,"tag":422,"props":760,"children":761},{},[762],{"type":386,"value":763},"Connect it to a device to make a wifi bridge so it can be placed anywhere?",{"type":377,"tag":422,"props":765,"children":766},{},[767],{"type":386,"value":768},"To get IP address:",{"type":377,"tag":587,"props":770,"children":775},{"code":771,"language":772,"meta":369,"className":773},"cat /private/var/db/dhcpd_leases\n\n{\n    name=HDHR-1096506C\n    ip_address=192.168.3.2\n    hw_address=1,0:18:dd:9:65:6\n    identifier=1,0:18:dd:9:65:6\n    lease=0x676c58e4\n}\n","shell",[774],"language-shell",[776],{"type":377,"tag":592,"props":777,"children":778},{"__ignoreMap":369},[779],{"type":386,"value":771},{"type":377,"tag":422,"props":781,"children":782},{},[783],{"type":386,"value":784},"To forward ports:",{"type":377,"tag":587,"props":786,"children":788},{"code":787},"#!/bin/bash\n# bit-torrent port forwarding with mac os x\nkillall -9 natd\nsleep 5\n# The following will forward 6881 to 6999 port to desktop computer located at 192.168.2.2\n# 192.168.1.100 => airport IP\n# 192.168.2.2 => Desktop client ip\n#  natd provides a Network Address Translation facility for use with divert(4) sockets under FreeBSD.\n# -------------------------------------------------------------------------------------------------\n/usr/sbin/natd -alias_address 192.168.1.100 -interface en1 -use_sockets -same_ports -unregistered_only -dynamic -clamp_mss -enable_natportmap -natportmap_interface en0 -redirect_port tcp 192.168.2.2:6881-6999 6881-6999 -l\n",[789],{"type":377,"tag":592,"props":790,"children":791},{"__ignoreMap":369},[792],{"type":386,"value":787},{"type":377,"tag":422,"props":794,"children":795},{},[796,798],{"type":386,"value":797},"via: ",{"type":377,"tag":434,"props":799,"children":802},{"href":800,"rel":801},"https://www.reddit.com/r/HDHR/comments/o4tuls/hd_homerun_to_plex/",[438],[803],{"type":386,"value":800},{"type":377,"tag":805,"props":806,"children":807},"blockquote",{},[808],{"type":377,"tag":422,"props":809,"children":810},{},[811],{"type":386,"value":812},"There are four ports open on the HD Homerun: 80, 554, 5004, and 8888. You should be able to use remote port forwarding to expose these ports from the remote system on a client in your Plex server's subnet to make this work.",{"type":377,"tag":654,"props":814,"children":816},{"id":815},"change-in-strategy",[817],{"type":386,"value":818},"Change in Strategy",{"type":377,"tag":422,"props":820,"children":821},{},[822],{"type":386,"value":823},"Evidently, the data emitted by the device is to heavy to go over normal wifi — it is not compressed or not very compressed. So trying to forward its ports is not productive as a means of making a wifi bridge.",{"type":377,"tag":422,"props":825,"children":826},{},[827],{"type":386,"value":828},"However, by connecting it to a computer running Plex server, where the Plex server is connected to the household network over wifi and the device is connected to the Plex server over ethernet, the Plex server can both receive the uncompressed data from the device, and compress it and stream it over wifi.",{"type":377,"tag":422,"props":830,"children":831},{},[832],{"type":386,"value":833},"This works! However you are still struggling to get consistent reception, at least for channel 25 (Fox) where Super Bowl will be broadcast.",{"type":377,"tag":422,"props":835,"children":836},{},[837],{"type":386,"value":838},"Your house has some vestigial coaxial cabling outside on the west side of the house. You are wondering if an outdoor antenna pointed north could be attached to that cabling?",{"type":377,"tag":422,"props":840,"children":841},{},[842],{"type":377,"tag":434,"props":843,"children":846},{"href":844,"rel":845},"https://www.amazon.com/GE-Directional-Mounting-Included-33692/dp/B00DNJZ58M/ref=pd_ci_mcx_mh_mcx_views_0_image?pd_rd_w=GZRtJ&content-id=amzn1.sym.bb21fc54-1dd8-448e-92bb-2ddce187f4ac%3Aamzn1.symc.40e6a10e-cbc4-4fa5-81e3-4435ff64d03b&pf_rd_p=bb21fc54-1dd8-448e-92bb-2ddce187f4ac&pf_rd_r=PG4XTZT6NVXYG798K3Q9&pd_rd_wg=JveeY&pd_rd_r=8d9919f9-62de-48ec-bd16-e34e4318c06d&pd_rd_i=B00DNJZ58M",[438],[847],{"type":386,"value":848},"You were looking at this antenna",{"type":377,"tag":422,"props":850,"children":851},{},[852,859,861],{"type":377,"tag":434,"props":853,"children":856},{"href":854,"rel":855},"https://www.amazon.com/Antennas-Direct-ClearStream-Multi-directional-Adjustable/dp/B074CQ5LCJ?th=1",[438],[857],{"type":386,"value":858},"This $100 indoor/outdoor one",{"type":386,"value":860}," was ",{"type":377,"tag":434,"props":862,"children":865},{"href":863,"rel":864},"https://www.consumerreports.org/electronics-computers/tv-antennas/tv-antenna-review-top-picks-from-consumer-reports-latest-tests-a2799732155/",[438],[866],{"type":386,"value":867},"CR’s top Pick",{"type":377,"tag":422,"props":869,"children":870},{},[871,878],{"type":377,"tag":434,"props":872,"children":875},{"href":873,"rel":874},"https://www.amazon.com/dp/B074TWSQFM",[438],[876],{"type":386,"value":877},"This $25 indoor antenna",{"type":386,"value":879}," is the wirecutter’s pick (it was CR’s third).",{"type":377,"tag":422,"props":881,"children":882},{},[883,885,892],{"type":386,"value":884},"You got ",{"type":377,"tag":434,"props":886,"children":889},{"href":887,"rel":888},"https://www.amazon.com/gp/product/B00KWFOLH6/ref=ppx_yo_dt_b_search_asin_image?ie=UTF8&th=1",[438],[890],{"type":386,"value":891},"your antenna",{"type":386,"value":893}," in 2016. Would a new antenna just be more of the same?",{"type":377,"tag":422,"props":895,"children":896},{},[897],{"type":386,"value":898},"You are going to try setting it up in Simon’s room (2nd floor, NW corner). Many articles state to just try moving around arbitrarily.",{"type":377,"tag":422,"props":900,"children":901},{},[902],{"type":386,"value":903},"![[Pasted image 20241226114241.png]]",{"type":377,"tag":422,"props":905,"children":906},{},[907],{"type":386,"value":908},"Although you couldn’t get both ABC and main PBS (channel 2) you found a spot on Simon’s west wall where you could get NBC, ABC, CBS and Channel 25 (Fox),  mostly hidden by his bunk bed. Moving inches up and down changed whether ABC or PBS was received. North wall had better PBS, but no Fox (I believe). Ideally you would get some small computer (~$250) as Plex server but for now you are using 2014 iMac as Plex server physically connected to HDHomerun Connect.",{"type":377,"tag":422,"props":910,"children":911},{},[912],{"type":386,"value":913},"Watched entire football game on ABC. Experienced 1-minute glitch coincident with large flock of geese (!) but otherwise fine. Not as crisp as YouTube TV or as uncompressed single direct-to-TV OTA signal but acceptable.",{"type":377,"tag":422,"props":915,"children":916},{},[917],{"type":386,"value":918},"Using power for antenna may be unnecessary? Might help get more channels, but the four we care about seem OK without it?",{"title":369,"searchDepth":736,"depth":736,"links":920},[921],{"id":815,"depth":739,"text":818},"content:notes-to-self:hdhomerun-connect-duo.md","notes-to-self/hdhomerun-connect-duo.md","notes-to-self/hdhomerun-connect-duo",{"_path":926,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":185,"description":369,"slug":186,"date":927,"dateString":928,"encrypted":368,"encryptedBody":372,"body":929,"_type":742,"_id":971,"_source":744,"_file":972,"_stem":973,"_extension":747},"/notes-to-self/movies-to-watch",1731776400000,"2024.11.16",{"type":374,"children":930,"toc":969},[931],{"type":377,"tag":378,"props":932,"children":933},{},[934,939,944,949,954,959,964],{"type":377,"tag":382,"props":935,"children":936},{},[937],{"type":386,"value":938},"The Witch (2016) horror? No jump scares. Anna Taylor-Joy",{"type":377,"tag":382,"props":940,"children":941},{},[942],{"type":386,"value":943},"Jackie Brown (1997) Good like pulp fiction",{"type":377,"tag":382,"props":945,"children":946},{},[947],{"type":386,"value":948},"Theater Camp (2023) like waiting for guffman but less funny. Sedaris cameo",{"type":377,"tag":382,"props":950,"children":951},{},[952],{"type":386,"value":953},"The Thing (1982) for Oscar also the original The Thing from Another World",{"type":377,"tag":382,"props":955,"children":956},{},[957],{"type":386,"value":958},"The Lady Eve (1941) screwball comedy Barbara Stanwyck",{"type":377,"tag":382,"props":960,"children":961},{},[962],{"type":386,"value":963},"Invasion of the Body Snatchers for Oscar",{"type":377,"tag":382,"props":965,"children":966},{},[967],{"type":386,"value":968},"In a Lonely Place (1950) drama “Bogart turns in perhaps his finest screen performance“",{"title":369,"searchDepth":736,"depth":736,"links":970},[],"content:notes-to-self:movies-to-watch.md","notes-to-self/movies-to-watch.md","notes-to-self/movies-to-watch",{"_path":975,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":287,"description":976,"slug":288,"date":977,"dateString":978,"encrypted":368,"encryptedBody":372,"body":979,"_type":742,"_id":1010,"_source":744,"_file":1011,"_stem":1012,"_extension":747},"/notes-to-self/sound-effects","BBC Sound Library - only for personal use but can be bought via sound effects for $5 via https://news.ycombinator.com/item?id=41646238",1727280000000,"2024-09-25",{"type":374,"children":980,"toc":1008},[981],{"type":377,"tag":422,"props":982,"children":983},{},[984,991,993,1000,1002],{"type":377,"tag":434,"props":985,"children":988},{"href":986,"rel":987},"https://sound-effects.bbcrewind.co.uk/search",[438],[989],{"type":386,"value":990},"BBC Sound Library",{"type":386,"value":992}," - only for personal use but can be bought via ",{"type":377,"tag":434,"props":994,"children":997},{"href":995,"rel":996},"https://download.prosoundeffects.com",[438],[998],{"type":386,"value":999},"sound effects for $5",{"type":386,"value":1001}," via ",{"type":377,"tag":434,"props":1003,"children":1006},{"href":1004,"rel":1005},"https://news.ycombinator.com/item?id=41646238",[438],[1007],{"type":386,"value":1004},{"title":369,"searchDepth":736,"depth":736,"links":1009},[],"content:notes-to-self:sound-effects.md","notes-to-self/sound-effects.md","notes-to-self/sound-effects",{"_path":1014,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":344,"description":1015,"slug":345,"date":1016,"dateString":1017,"encrypted":1018,"encryptedBody":1019,"body":1020,"_type":742,"_id":1032,"_source":744,"_file":1033,"_stem":1034,"_extension":747},"/notes-to-self/what-god-quantum-mechanics-and-consciousness-have-in-common","John Horgan",1725465600000,"2024-09-04",true,"HrpAMOxEx_-hLcIP5oFEqNIq5Igjx95e4PX13vyEV3IUBdxYI0wsUiflFxQvh2YcQ2iSgSVC9mVXSxqURku_sy0-RwzmGaWZb-9AT2Lrl7ga6vEE65KMsokc4TEWSkcvPp5iFlIBzEIJPnpEZMmRo7QWjHFJO7dGv2t9-DwUxHQgjOH-b_b0ozTzZG6cdaajSr0dGSBBg6bWmPPIA-sA8bYYuRemTfmGblKBebK1FYXvuhbGGlvGV-_NkFHTKVauoWHuqi_w6_jR-3JJQvZpAD3YTajoxSZlQ-XwTqEHJ9qt51cUUZp0otCpJQq48EzAa7Y3wAo4pqWDIxP-krd_uV5PVRiWi-23qI_wjvueaK3jZWBUER9lkaDpFBZjrCnFdnuh5MFds6IrLzdQLK_QCCH3RmLQaIg8zXYFuSaktBSnzx_5QBUYTYMHYpGv_DpXtLveyBmEhbUEyyKowNhy177q2ZT1-3TpXGCMuJsaCKcXs0PARSRFISkvHIP7o3CpxD2S8gFcz2oSrsjZ0sVLU0ElSfqEKV0WznLA3SjN_GHuBlJg2nflvZAih_ExYlfixARAno8RyoWL3TrBSxlORdYqGrNDCAHHJP_Vn21IWOckUzDUyiuuS7XFTDcc17kpRbH9N3i4J60raeqIBPwc6XJNHM89fgWP1_jTSq36qq4qTqU2lBQSxW9WeXq_rTeVmTtqZIk7A2Ht45xc0aPscdfDgC8FZQg14TaM0Gq5K6Lk4R6qiwXDhW-kiZWZo8a9MUak_1TPmS5Z2liJG0lczTXPN2vXgrlmt9GXXcDwr19rtC6PQ7iAwM9rQdcCOWiNpUhvA8Q7EoXY5V1gewZS1Y_EuK6KSrwWEnaDAhkM5vM1b2r3q4KDRi2s679v_5OGQeBME8QB5QSr6wsNdwPchPldAn4--kTCmgY8yePZRmMEhg7wxB4BP0ha8irkErAAaVDqit8yNe1eiIx2nyaNL7D8JOCR7arwRoPNzDdvIgRX_YbOWdryNfVydO_4yBpeV3QOT8qhxLBoL7u76y4XyXpHNEODC4uV7PqRJoIeiBBTK77uBtO8g5PmZj-mAYTbbQMpibBXfCKP4EV8sIl61D0yjL-lOEHBqJEGf5kPwoGbmQUGMv216ioUjkmPq8nuuGk07JZ_NuohteN1B4vhSz_kAaH6bKU7qqaeh6M93MslPk2UjMFAG4LIPwk7Uc7JjR-kjJ-O-wJUCIqKwyKK8n3RCAYtTyCI15cZfOVLBrjHE3ucgMWKYfsXUzTq9uz7TBl06HVtI3HwUX4egvj_OTUJXjSD8wtGsFiRPAAcsYKCqaT-j1RcJhRxC1xkn9m68MLx3QMNSpJZ6vOAVCM2MuU79YD5510Zbq16lRPJPO1e_eQ22jKYSLuEOONztmC4xJYGjrGWl1hflB4PJr1dkAQDvpP25nlKSN79hyevpckOd1vtrB_Mvu4TNgFEpsu3VIKDh0fKTnk489GrXzTYkrtSKyfZ2Fw_8evnqAWnaVwirgDz3y3Yh0hT6JzNJphYmaLZH8oiZor4njWj-AJvC2554V9PVEIjmOjTNIWqvhRp-9s8I_CHbhHrr3_xJ2Acv7fno9fHIWoOKZbz9R_-7D9pCb7wPr8PaNnlr-AdI_cttOOQDPlswvtzRIgazwcumTGzjPFy3yyZz_UIaTatUdzMDi5ZeDDT4zwvuQG1ZoV4En5wmJVreqfTWxFFl2BK4txa1Xpn_o0NW3wDDdIll4xbEwIxWuSMKXFR6DgkYoZC8SdYwbkLB6Qe3bN3XOW9cwCDFAUCrr8lOmuwH24eth8KTnShV2Db-MeZinxGUK6QfJUcAyDl5yk-9Y0X53nL_i-7LJxeiMrAeC5u2eVPwhJZuWnlEFHTQzM2vgKols9dEK9bJrvTur1yooTxO_w7PvDJPTHBy4cIjclsgXHyLuh8tOsyUe-cTVWxJsOi2AwkrDxJBtDuRmtLwMssCmIpph4AL-c-_dih1kjQ0oCLTjBPodPSLk7OM0TXMFZGzkDWv8DUzS-0IR-SSV4nWqwuJS6pIWY_HqL2SMqxOSZPKAaP8S9dqxYn3kgDLnqt3gFJ85Ucyb9oHxgAr6Wg6JkH7-kPChQc3GT4xmwnm9DIHV1iXwTUkifCj1oi5ymEq3aQhd3WdYb3hEYiQL44v2EapQfRvKokcd9RXAzzvb5wg_oR0ioovOG8Hv7WCX_mQVI9c4HL204afPSX6UhyK7faBCbcRGA6IN72gbI0NQTnu0PJs5EgIZmBlkrcc8JVL8JJ77IFGoKRu8FrZOvYpcVza7f-wHIFGwLHexjOtDAG1pri1ocm91EhY1oOdUMMgGxz8461Gdjr8cbgdnz2K-r2j_0Hb97NNbHPuGV0DSfEU4ltqQZZRNpIcyJjq3_10jcZXr3lFMLRKMsRf-V7VToqHaP1AeHDQMJWw6CXdf1FR85ZEB3lJKKh0ekwW3wPXfX4SvCv7FavYTTBIf-AGhBtYKwcZQnfcZoWfPJec12OAEFEusi0j2LzmiOsuYYeBANEi5uG4MmepgCMbmGbLyGgDvF06IDkj35_JZlTvqhyumSo3pvbbQWbXGmglf6Ymo1JrnPn060ehkYBsVUBO12XHyKo6v9e5K41_v31BCb3EOwRmz1ORISx-ANkTLJDaoeu7qD7brfPxi_aBVpHaZ1JlQeVn1v6pQpX5_7cyxKhRw6HNjacfEPFgVDj1GAtlhyfOZyrFx_BnsQ6XcvZHXiHlzs1xnccvjJXcEflYS2rQOx_PTHI0TM2OZOMn0g-nZtiucH5i_5r3R73Yu2JQU5YF6x1UVkqsw9zEHTL-pgomHn5hXRuAcQXUYDAb7PXEdCQr7XmDXMT64B9orFI1PcJ-j3lL2hGAPW3i41WEcCEoMm07j5DDLMxHYQWnptMOt8NdNJwTDaNu4yfJOuP2pVnqO4HWIBN4fUvXXnbcNEbttK3lStekEzJyxY5AhQG9K4uS5O6YBllDcMQlzKQuXeTkRDhnjB82dsBvIYkm8muQRhFpxIKr1mnlm0d45M8rBkdGBLDAVD1PR8chO0f11HNyvMBRrfRCSNa90zoJWVKGZJGMQPvZ2GuBItogOqOUhRrifau-AUjG85hzpv7nQuCWOa385iEH7j6IppiH9lLTHhxj8g0T7Xcw9T9mZ4BfY2Pgu252LPQ2RgXKY5JFsv0KewgKMW9E6RALbPpWiH-6GSb_j5J_sM1nJ-icwifV4PS5DOizw7YwSfQuSpodKm_FwoUQIcm-Aqkw3RuR2gBUb3iB6WbZG_EbkS2LtWs0s2GTy51PLdPpCiPYV99dLEBiEfvsJHgDZU5ceR9tT1N_LPbDy5fRgBA3PT5Kts6GUVTshW25xFMcx3qzdfmPN4YNufON7CMuusCtc87w1zk1gPoC3Jycl3DZvk_7VrzDiykwRnyDO0CXb85596bwBsZlsNsXjRMjH6DqFXWu80fZ-khyUEF9BzY-S_3cemMDNyJBosJzSsu0lfMqnI2-Kx3TgEwBuZvaHg-w7-8Wl56Cvy-8RNcdlXYNPFzXIXwDpLexieYO5UBLJq2O3W4U8EhMxdMPID-pYTNtxQYzay2jgkoQG7jsIehl4FEv62Z4QxyDAoZevzCLxnLZC64yuoK7cjbwZTQwd0nCCcQy7MWojm_1IjhATc4T_sIkOHvVJxp0wT5GFa_Xd_wo_rU0eKrNMO7cRQ5Bm_VQIH-IrVXaLvP9tKzZBhIlS14RVi-VCK3PRO4dVgbaTAIy_HXhDt1_TTuZrlMVFwP4BjZ-LSKDb0hT0cxvxuROwekTR3QCenofMVXSf6ErEzxRJuzlCxyBDuq15f_absKTxD7h_W-aptu-7G_8R0wohk53K7Oyp2XgNMVRYEH7TiF68BUjtWCNLfAzw_vd936Sg7-SsRsgrlk13D_wF7o_SRdl2r9vdXixtrS-OjZbzHGg9FXMMv55hgpChTWBJ8d6QAKh4kChA-H8-_4G-XLqqHn9MoRjiaB3VDr0zGMmdOxdUtomNbT4ScsnzBIUJq3aFmdGD_2DoI-1n5qrnowfUMUtbR53qWPMJqNNMqaceHSVsZ3d4pu5i4PFcs-GgvTJQiM8goCc5PYHf3hKZJQTzyKBoIlksTPgi_wy0NWjaK6rs_2HogmwkLuj451zn8B3Gq_HypHIl8Xg5OXHKEG2M0i2IgEHPXq31XXCjMbrAIFPMrnDVHLrSFs4BtDmKhPykvcW-hRYmg6WwFuqyIgmkkguOcHcvwc7O5MHLcpdl__d3-_OZ6GCGLObVQUANYSLkDkXsTVAqxYDSv5CseExfwCLlPzH8b0b1Sj4VZyjs_Xae4ZjSkfJ-1J86dwqe6WvjajZ_Kz0m3Q3h0KnrWBdiQEEv5i8PNfGFsV6XFLsYCLLyiiHTkHkpB67xd_XeNKRAkSZ0uQQgcmdh4X_NJFrPBSFwMgy77tD-ARBZlPtgoW8Imhc3UuusEWbOurAcYvmlz5bf084TPLEer5GgcQPoIjaiSUUL-rnvgHQJbxjFMaD_GuVVtn8IEFPuL6fI111-UK2tJ1pORt5kjPvuxIRis6nu7fwKaUVYVUoZCaLxbZVOCKF-ofsIYSnfi2z7qBd3KiSBTgNn7SJVo85YjKCd59IjcFoW-NpZNkRBmH0dyoq6R7P0-Ib9VoIZSYlUcDlQEW6i8zQLmuXQHefeQ1-W0v8ozNgceGwkFXuYLXjQuqwzJeZvS5YK-u6-E5Om2z5iQ6e7DpK0n5JncICJG9YgxheLt9PzD3cxwSVuWd1sRy7Vm4RHa4nEyL94GLeIlqWrZHtkAHvtegY2CgvfUEdVw_-pjdrzS967Z7zOfIlnWGzFBeLvJ4htoyCrCDm_0EtLhuDdWJBvdoVzqyN3nEhf89cHB8GMP9NDBO5sODpljo--spbLP1V_WujZyOO-AV238HfjjyGttzolQn34UTjymEhNBU52Yzi_tUTJwbdSJQQLMkUPVD0Uqr2Sg42jGkyiO5LehMKf-ZeU-BSrDTDCaRjycNZW-1EWKYxt5qqkOf7kRUILm0r4QLCfiHcfldJkrTv2iMBVL3oH5PXs4cQy4GGw25so6mqZBJxHzlxpyR7iQ91JyIAt4R_GLr9bHpy1t6E0ImWszEsD8URLNi5oZP9EmK-kTeVJFmj7f9A1qcwqkGGHSTXUylUrA5dH-Fvca67qroUrbC8s8eBuCDg04wPKBmfY1hBNngGOmk21fyzdXtHSoNGDmrkON7kBfHvewH8JDvUR4l5qRIDKzfVTtWGes6qS8cK3W0QRF-7P6dmecEwtWKqKnmtdEttMrwC4SKytNZwl9p8-YhC1RIDFmWfDbcfMXs8u0iquIr95KrN8iXXTlxhsEFSjNgOna5pGlyuyp7jvLtsQc4ngXJND7yjXgPh7f8O_DKKo8L0uQKU0wbGPt-GI5hUqT-A3qRGafXjq09-hLJ7GtPfXBiRegepS-8Q8AtZFpT4TLMFsH-riEsxzLODXchLcw4LD6tYKXPqjkK6FWCEOjAiiMM-cgja4uGyZhjCfpZW1fVGPZ1ztvVNUV8-QN0K0FK1DG4PvoxX10_bOEq386QE7JsvhfszgiqIV76jV8Da5JBWeAsB0qHATNHIXsQQNOebB6aENmhioFwkF9mie9lQuxSF6on_Lb_26k93gm0u7eUCQMpUn20zeWcWkMuuBTVmcxAs0OVeAyex-bOTtu6ota5m02sYoZEFziqmS9W5febCugdtWaHv9zub5X-E4DjKjo2LPMCusl72bM3NN4i7IoIJnaA-UV_KKp7Cxz4RDZuBCkoj8mUQ8gm7sTco_fdzdRaOiGZLAorwwUO6jovNnUIePV1FQ3sz0Wu8Ua50ziifgSoU6Utph2xaQdbHb52cMHQRPTSc1LN7Y0iUFziyqytn0hIKj36YzqQsrERCR6_A8LHlVWhEW1Xmqf8rgkOKbX34cAg8YZ6IrMezTBILdacOwPswPmvCXWOcnICpjGmaN_2i-eVcEzef3iO0wSBhZsj3YSfAqZS3Zl2irliX6Dk3-GE4hNqp1B1XNc7O_aou125_TC51PdRqUU3X1JyVRVIMfJwN4ieSaVNO4t0I-YiFuMV-GuS5c7_7BdCu-IOkFG1i09ZSP0w5Tlia5YItpJMAeLU6PF3l055j3xrmGCLQ4VCv6UmBmsDbbf9LYvCdwxbFJk6BkTFlKE8xadceIPJ9uoAhkOQZupZxUAP47JwzokWvS9BlZZK5j_4kxo7plvX_EwAhcqNUsT_FTbHcvkZ2O0lrY_tKcmcMpJtpFg4za1U1r-NmBfshtcpDp3RMaJ9F2-HzzdWCsGs6BiCPUw1tlbmNeIJFbCUgwe4dtf_qKWefB8QpOVMe_FGEsikZr8KeXxFrBvV9lLRhSkpnaLArg0vnLq9YDdI-zViBxzUyy5b6KnmjTT1O_F-sYm-E3G2ULokJszdZenVPRMmNixykatn6k-7YIfohdB2sg2Jvzy0NO1X8J0qU8lB1IFsaBz1G-7dvT4ZC6Qe7CK0cf9fv8uK7TjUopLukU3gBmqWa1pQV4naZQUUED1GopTeQeqhBoAxWHaOMTzmEHnYZr0nmPdqcYPAi0Xtg8-uo5v198V0OUgHYD3dtcQwCEB-J6bebl0qExlzgf3C0nEjdPzUCSqijwVIU-JgElRIl8VQOuQmWlDtydu2m371FlfliuGqxoZ-DArpyK-TAaVnrwcea6rWCdtXuTAO394f-BxrE1VMwvdKGS2ww9mKdQai_IGkwO6iYTkaEkFNG9ayIl3PcSYcej3Uut7Aup834oZUq0w1oJCpGrAZLRGRCHhotw8OHzljpZrxWXtHguvKAT7ZiEiPZDOc3FX_1IwG4XT5YpkVm_yAIGtK5PYW9GOcGIUxPCV6FlEJfB0hEHgDH1_0nBmrHaidTpCZM_SgU5fl-nvsYfrje7fUVnF_ZlyqVhTED2F_2DKyy3ydft-D15s996sxqJpefGv8iPNoHwQn-H6rF2cp-misBTvF-ozJ6-DTSEPocrlPSvkrm2hOIyE1cE8U33PLXCqcbrEcgPT_28iOqm3RuJ-BKdiK4Jt_MnDE96OlL8YcqBcGkth8JUfExkt7pNAwsyYfucNheRDDYJTI96SdnGKS1I8dqfqdxmKfl30UFL6BdhVLWqkU9Ih6c2GVg--1RAAZfCGutcyBdCwfdANFaGsaY8fiz_DX662yIkazY0Mw2SrA3NomuZpdCEWpyd19z3RQLAgY1aSu9qIA9pP_qfnpqBhuKIiPAjJwbRup8sOEbNAnh0EbgWhNcWeusmL9SWxQr_FwKHm9RrZIpf3I25QtS2uaixrBr2TYCmoJop3dFH9M47V7LXCEFOuLL0RwpHyaD-pg9QteNvLCPBpdgTVeqpfnh5fbmfWajD9A9VLO0QChD9dOwrO8hzkYdlMsBcX05amHHqQD002QHwv3SGeBoQpG7WLAhqXFc41FIMi6sfGuR50446m5AeSpzxFYcbmpUExt6fDGGVf7FEwm78Qv2xnFq_Ygt4_jxKIlmmgrCaRVKfkTrG3HNBxP7KjNWpUAtQKsDcsB3MY1IbAsqUE0hUHS3lniSULkL5OBo2V6JaVby73-q1JKQkTqJ_-K59EaixamDJSM9Ui_XWlzYnK2O55LiEGu2doS-tHDagV6BBMvwG-3cgPfyAScaog1VmNg_bdAZUTy1QDXc7DMl2aMb4TYunDt722GzeM8uzj-ty5y3GwvQUC7hxDX28bJcdynhmj18sqJu-TQZ3i9BGKfg0p8hhOVb7azS9XS0XaKimrnbBDp43wnLIc7H_b-9VAhFqX2rwVtU5TsU_BY30oBh6_FuMJgFjHlpRRuFCwqHxb2ZZ_VAKlbBIiq-48RWyl-02wzlZffqe2dAbx-lzwgWI_c4sppTXrGuzuRdtYHTxkYNEFpbQ_YZH5BmhnYOF_ubYrXtrd9CReFlJ1KoVhp8U3bxwR4VToi1XNe-47Af-wQdnS6ukLZfAHLPe9TakX3pFrDEMO0a2F7Kab6kEDPm5PR66KWHlk3cr_ljPA73au18j8yA49UZEuTh0H9HgRYou3O2kN8dNcscKsS1auf91MhJ2UcrAzI5UgGs-SHMrdfxgQPT1Df79ldOrjN6Ue3Y4CsAz_2bTJhitsr5EUZ485Rj4wPkT7qxAHgXlab3Wx25cThDHgdanCwoxDl7r6IY1CI44wPfxIsLM74VLGZsjRF8EYlsNZDzkZXMfiSOwI2xnNXr0LuyPJNSewZRGc_gm_vBwQPG1yaOmHRY9uevqi_Sp6l50_I_MCI6IXxxopx5LOWEI6qFAc3ljj4Mq24ad4s9j3udNqmAq0JQ4M6cW9CcGvugzuCTBgDf1cyGjPURRGjybVmc6gk1lMtnVGT-6uA4TSSLySihdIYFwaltn1XNC9Xz-YFW-SAeeYHUEKxq3didxdVeh2kuFCqf-taW8Ci174jMMHhO5sGSI4z-_C2rA0gWNpbOz5i1YDurWwZGR95HzzKBrKaPutWYb0esdFM-FInC0L0tfeky7Fa9s8wNGutj3aXKkYAU4Rzpfz0a1fdhCjMjTqMLeesRn-y87RR0iVNR6pn9eBBysL_0fWWB_XPZEWRbjfrAtH8uCjRHJDB8Fux-Rg9Ar8D_sx0ef--rThB7ucwZD3X9SGBh7oXARmv_9R516UZeKh57tDCg1ReFTbikUHj2yZPl9fFlTWmec2aqgneLZg28AgCpcQc6U0uR5CCuiyKSamOn_bJVfUa8aLCk4lsdEZ7-cN3n7-6oGZDnfx8MGqmYfCZ05rm-pZaP-752-vXtBmLOV_7DiofOUVnG6RC8GfKU--k22ga_ThSDE4RsAd-YFewK1mtItDPTIYkNMKyd9EjtN4oac2NDMcniT-DB3FCSI_KthOMT6TjtFQudtXw6dKPJtCgvt9L5L2G2H0bZM6LmZfV8BD1Kj0ZuVFEdDI9OPw_w-rKdlqV4G1y19ZLjTBKMaICE0uE1nvbvG1lGcgi8Uu4LJDKzNNwY15RahHhfLe5pm95H-EtnvNCKY_pMMYwUziHKYcQLftgAvZi1z1YPE74jnUcM0DdvwdWpzSffbSXAYGMPrUG4a8bqRHIcfLSOW5SStKAHWg2UHBjrP4SoG9LJyOt1zGqwjkK19O-Bvatx0_YGn9naT7wHhtI7HMAV-v4Mb5kEd2all9cAy61COwsp6jUXhRDIddop9eEA_yJp3ynZWPqmwU_OToOdKrJPlTvHnwZlOcqZqmxsG11ye1Xb5r7tqhPVgyztaPrYRfAsXOfMN_KO5poG2z9UEEuZPXxJ0a6IErUvJwoVn64Yb1hXbuqK381XAIx4qdNv1kr2AHmDPi-jPNZBbPjkk7hktP6BJ0T1WCUel6D1VnXgu9ess7JPsso_MFhyLIIXoYldVdigORCoMkwq5J49wTEFPlPIxfT-EWpeiRWmMVZjXX7e8lQA8zFzwCsM7U343prtbPqJRuOwMI0nQwLThOr6p0Y3l_dkmbmtpFZaVWhPOJ1fz1u1SpUukdmUbwxYFLUtYWCAYz5s9xqxrwpv9q7TiFGVUPHXk3rjkHZ_vinUFN43rsRbPJiz_GyKmovG3l_wCW8-pXk9S8QVngu7K24V18obVHcYuVgzj-yWaTNT9zCGU5yHy6h3zuE0yxw_3z0mSqE1uxb6bnR4VkQEI2OEBos-5H4ppbOwa2_H6fEOfaOJXUtUMcH6IUjlytsx6f9jw2pDgt9bK4lvkwNSdxUsz5zj3TPJTCidvJj5QuX7mal8xVMkDbvnk1XMcoMvSp12q9lUPaLjQJfNgFweKLYGIZNVoSIw2SSZlU85jUZcsilV6kEYYfaVxhwXFovWkB_DxPki5tv8U4UkfxhTc1bCgSeukEQbGUxXcuyN7Ve7WrxmP4p7-PBaP6Xvut3d3he8uckxNe932VWLkZfHMyeSMJ9wFj0BXRR8GMbrc7vJFlkhGoAP-qD9APYgTkqP2pLukqOwyRtDh4CzxJHARUJpAnXvSIRgiB5wJyX0AggRJ2otTDaICVWf29XcWdmeku_SbIgkouAhjBKp01_OHyHiFavkmeGJFaJPUVkc6vA9NyIpnhhfnwIvo4lbhhMWw-Nv1eMWJMXlSTgU2N4uF2G7eXb2czejOH21wygL339Oikkn3BAQoGlU0KE3NbRanBIXJUWWydwcnWClhDOpgZCJm0tbIm0Y9G1j_MBRyhEKnw0ORQXDBpNRnA7aDFr_BetaQdh34Xmg15x5fxV7N9rZrBNaw5ZWEoZejuvF2czTyh7P90wB-dk6Tr5FiqjxFjTH68GDoGoXG9HT5ctg8JUbld2XYjIq2N6ZeKQfHe6Lxi0VOv78hVTiquD1k0xTkzJ2ZL7bthZGcPiZAAKel-fDFPYQIE31cnwMtS_snvQeF_lz9DNuPg90YJQDrXBDWYDTDyzyIzraFDm5TS2QTG0iH9jI2U4xwZ0mtIgW82rPDcfJxIXkF_hdaqonDuUYA5FR93_GsbC7Fe0Hanbu6baFwB5M7PKLzTyVXorO6yG88_im3BHYn7PtNVgDSJNig-FIfDRIZAbeb0cnBV_i90_5ZuhsyfQ8o_dGcZDKbgnOI71zdpCXpdcqp3PF0CXcRr6YqLYITnJWd9aT2O4UNy_vJXaIRlCR09sBGPtfNctdsiK4MQyj7MMi8Ol4iLXYUbO2fkneIvaMRSEOWtZy0vDfA4OSJMa62N3w4QtWHgd5bcC3FUb32Qm42GppAxNMMuaKumhccKRtjLW_GYNq-9dpFEsjSkU2OsOhfgv_6a7OsIBvrKGthlxBsy6cp4pyNRz8k5EuMi860MeTal2G49Yt0ykJ_nm_W8Pd6XG11PzHcQNnlJiYlWR_8t63o50n_MNQ8XuLcx6n0s_mVIlUriKW0EwRB2Js5SMupesQskEdeywkP8yr2p0RI_cP-7dEd44vENTT-dwj0k1JaBZgiNK6Jf0JkPua73nsnZimDHCf-JVcYjAnHU9TnjhKwQf_c71IuBBLu5vpFQQNuZZlOPQH4pFpZJPdYuYXRVTJMee1vkB3eMPT3NH8xzxNg1wVnjMmYeb6R_3TaAwCGKa3kSbhhD4s3Z5a7ZPA7u3_56FsxH0fPYC2Ivr59aMhB5YpMlkE0v1DNnJp_y6BCX270M6J_a2i3J-_NFn8oPg65bYcMaVA7RK7fBvRELN_aEPP0i5lV4XGaVsjy8ITDvZ17Fwh7rtxWb2ersV-k6WEGUMDX0oLL8pPjyUSY1YLCmK1ANovkAmR5XQ6Vwc270W8KclknZCUSk4V8t9DgaUP6yYjDUOwB2F_a9fdrDEVCh1UiH-4n_FsRb3psSjMUAqTA6qmuipDkHal_czWcc9AH8F2pkaItTAhKr3sPzRmCx3iIl2kZ1mAc5A8wusk3z-JpC3CZFtTy8MBwZRdkfj6tcgxbSBc40Nm150-ZXxzQFgj6Q5isLKIaIx_4weYjuC4H85NMQy9uDPK5l5YuQKI1NM-re41Q38wv2-9gGsVaMlen5-6BhkIkhf3SXPymql-nK_Voka7t71_lqiqBd2RYAGXhev6sEHDyP2QtyLlj1d3tDOxXQQpBO3oBES1SySrfeE_82S8cDzU8yCyDDMIPINa_tchhod99oYbyl5PBlA07pGheG5zggCKtiYnxHlIGaH111JNNhuog5hPWKJ8fnoHe4vDTvRDXmS4WgB8WX1f7vEqdr5u6eyGHiFU_kqXAhFNoqrK9PUxrBko2oiqXVaOMj-6T87tJPfuwRNmRIHGP8zD4kE3IB7bhwnZ8y04UKFRdr13D31eAZEs0hk0eH8IHTwNb9kDmH0WYa-ZkEY4cAfqfeeptvp8Bi1oDEtc3RoG2qVnDBkxYcHsKn8jtzVgYj_olRGYS48u5aGwtKjTbACFtlkRX8DJ1tfE0SgohVMOcvBEtSIib_bv_ynw4cdeft5kfwcpyu72lP4-XrA4vR4Ugfw9mahiMvax6_rwPWwedPoJzp0Mokc4tDD4u5d2FgUhHn2DzShfz_0e3-5dqkYHVLoHGmRYcskYibUX_pFwOuIpTmKtqo3nDfC1rTQVyDn0ESTVkqsZSIUzO-nI9kZMpNzpXnbJvIfY8fYHnunjvv4DQ3OminYBkgKGS8ayH8WtrSduGxmGLAkQRFqJ8kMJ2HwGusXjjpTqR9Kw5g5YhiYySDL3xmwPvDjfiC_SP6Z-1iyIdAtNtCzTeQhjoXmFEZfS7FGZoXLBA8mcy6FCpuXJZAxLoWXz4-uEwLDxChct47gse6ARiyD34yPsWjZf7JRc5CP6BQpwNn_NIyUD1CMXOS4BVLo4GMIBIKkrAEHt-rbQaW8rxMJGrv9l21r3YF0OXIJ7qAqAESvfqpJZDsm49o5Mqm5bwW9_iXeIT2Zfbt130d0adQf0dFTTN42biXandys8fWIK0IPFcM9iIpO7Pg2BubanxKOmX6bfnF9Xmx9v4fMGlh31pSsdUMOWL-3733UU128Y_0O7q2tp2gOwpyS0RW5Tuh3KBjJciBA_WvSod6snj0fYXO0PLtA7_Tl4njS3GozgzdmS0jStIvsR21pCbIO901q2L3bynQL-i1XVruPnDTAFx5iXHGnPhDipjZ4fLqJckdGG0aVKKlz7agcELHPyREel50Ts1fo1sKsYS97tLivaKGXW1Fv8pTWpmFvjhtoSMId8JxO-jScBGrthnesGlqSgg-ZEG8mucgvUbOAaGpWOLbN-DWCuSDHjFHYTgAkOuc4iJWMjGeBk59Shd02IsddS8rQPY1xV6VYu8KrNUMIYprkoEGP9VWk7Z6MeAfWhEnqzgMRstdLFCynweAmuieZH14D--Ikjc-E48XPtG4cgv-_wFtt9m94dKr7q7OZparEWapuao-K-ftN_7dlAWy6wgi8CgjlIRo3i5fsfiQ9bqHDxI4CPFwSm2kdsNQ6DmyRpgQ-mVEBVnc8B3MI3cPL2ySXJyQyIB8v5a9SAuaQCJ_ARtgYQHOtZJAYkimOCsyE58ZuzZsjKHQAV0Ey1QkzlYUhbyuiQ4ZqNBoT3XQIr6PQkxpxlVLj4qgs9CfoUspSN_mwshZz0lWS0pI89B_86dk1S-UZOoQEQYW5Rv1bheVsq0vZrfUbntW3NBH2aY-qrtv4AkkzldoEOBEaw8ne7xOa5aYQC_EfHxy_O6GkG_QIWJlexStLabRSHhvtAHgdPKMP3XXWgMWwPIkvu3sh_bY6Q8vP6ewp9esibNjKP_GB0S0p7_XujYTG0boDds6_r8n21CB5I46Mbmad-umPfChy8vCdxn7wSbS8PLjsPrJa507JrFAfC0ttwgwEoczZo5HbMRI_5MPwgp6-YJ29BypTeh6NUZm2e0YgoJmKj7QOxsyLDcLR1fDggeklKvumXByyKqTPQJFd0PsJi8qMJwHvVtj_zzpwwnFUsns0QkgI97nxrtDnudBPIyS3P7BcB8fSOQm5StLm58rs9c6T47COgYJQdYUVQJ7jDIuGa9LbEpuzSYIYnP8sIyC-x9KkAbb7z-CqiCEM1LJlkvgEhZEGY3yT1D46InYHeZCThCBpV7Ux2vrcWCUsRVI5PBoNj1VYZW5jq1TqTK5cBsFM0srSkM7YXOZYSHhZFS-daKpNERWNDyM61yVh66uu4yqWxZepse9AAwdEf4g7h0mYrmQQcNcR-SVWSmWWox1jlj9TlMRk3mkBnXQPtLjy3qw6bVIJA1Rpdxi8mW-io0c5CVx7dLJs1gmC-SrFsG8BYJR_cdpoO2L2T3hmGI9AzjpJAfP3kqiG4PFxifX4Eg0Dzz0nfhSReRh5_KvuqnecxOkAfRbujBPsHvTOGmScfbeINJRWc1XiefaayQyy9wixX5tdc-52sgObDUvVU53axM52ZB2-pqujc040M58cJRCxk7h7E1rpktwKmxPgp8PsJkwzLu0sJlCZkqrkaeRRz1L1HIli9M0I_3xfhTCp2BrPZWK-e5bVwu6orthLtQHQBqUNEpAAlM2Rq3rqEr0wAwvJUPXEQS4h2ov2caxy_4GHfNoo2b7wg2yvML174saA9kj1ulEQNdxKl-_iF05A--QhGOVUlDPxJPLFw4r_yQJbe1gWGDLo5ai61tTkjCu0gAbcCkCEGCAAm1ggxwAMMHBmXY8Lh-5bnIHl4wIsH9W1UqZvFy_8eJuyD6lU-CtSRX7_YT8rk11Tx_y1_zmJR4ieb6NkeyEZqjpkM_Sifk5CVqMPZ_Aeem6Y_FrJ-mCVNgwn6Xfl_Qz-YWPFq_IRSyQUEQYz8eS145K5tyTxKweTVOwOp6jr_XgHlZjbZoymAQNDBm9S39jDFflej_5TfqqXzyRm3a1wsSCJpmu2nqERMJbhBA-Coq8NbtfCVcdiX9UOGYoa-065PhGXg2s8ZTJIKNpd8PcAg1hHsTK9HsCqWjieYfzh5vO_O56UZiHntWfVUfftTMCDv8JIOo4EInx4al53Aw6yX9wunxg_sFhS-9YxdEN1tnFSaFaluK8VoBO7JOuH-YTm2snC6B5RpWUoZzlEId6bo2IorGwa0xOwkkiqfBvpdoUzbhlvQzkXt1XFpeRFTssYmIlpeWQkSeTE-tlorn969GbL1u6LoO0Z0cIR94axEym3qnqsKsVI5LhYeoNc-zHFlPny_GDb2mdBSZlQt3SHCZSxMF37-BRdJmvNsJCU9zuY93YQ8yD2f1axyENJ_l9mSmGbLtuQZdqszJs7WeK1b8rE8Cveqq-NvnC0oGflkpDan4k-a7_hDZcUZ2S2qxFyZMXdWQ2wzYBdW3zSXSrTmRbbe73sqjst3Gw2plJrRfsB8aDvOQP16Jj1_TxxUaDsRYHXZ6WSL9RH4RImRMbhivfk7GEv05nLHPBRd3dEahlyXXiqibbG429a2YaanKIlzWZ7Z88LVLKortIWXc5-TUK10wPg8htVzz4IFwt4Y1j68_sc9eZzNggGN1sdeQ3BbsHgkC3SQqSrrShDBjv7SIGZU0QpJuGYGMWwzLTB8bRlUfux5CCnu4a9ixQG8IJZzeRE1sWVoWzJRGYhZABexnBLSXoiBNcKDkBCQ_ZNHceEtinHPXmy4VsIiZvrs7hjKC6d310MOSoGsS5FyJjDq8elqwIjzxBP3HBVRM79kLnX3UiWePEbUfAIq9obdegeSGC-BLFD8CnAAkUeLNnVC7rXygnbNIl0h__gfWhpdKPzV9lnX0q4ZEjNzku66cam8QU4OVzcMLrb5lzFe7_JgALfa9dYZuvSVVGyaktCMFcFGqj7kHNxtLe_34livWk4H_C2TojBN8OqgyK2qzAe_DYMyW2JN-gT5rZKnLI3vQdhu-pi4iIFJ0lCAZ8uxZAUjtJbuVA0yW6ed1rN00W0fZeiPl3Jx8rt5pa-vS98MBIgjjby3QKxRkILdU_ueIASfsvoHU74msSI5vvQ9yxT5Jtc2CmFk3mSDaCQt6vMw1Pcah5iWW0VCE4IDU3eHSSM_H_-IfN-weK3yr75anzKxP7V1yXBCEpssRx6rJDGsoTWjw1x9XDXfOmsPtgPJcyhvZAym--UfMd_9vZZcRT6fjjMgJs4O1wBBEglk4PbgnLdfFm0z2yvOPbTiJXUuREq7eLmfIEK1ykfBv2n716iJpYCv2a1GlIt-nL1_iWYBHj57TjM-pWwhFPppNiu7kZLJLAQ3YROEw_xB1F2GPkIE1Y0Mq6eIFzLmccA5NUKud47TvKZ8ykQqPMYOWWRgTN0Cf6zumwbhsYr8hSoxScUoPB9X9dQkQeaxxBGoikN14PK8bo78UQGsZyND7qRGd6u-v6eV4JnLRdNvbglI9R0mmfrHqrBNTxYzmBPoBr0nxx_ddcpJahUWyXpxSmNg6HdeBiUAPgteCPK1Y94wdTloIqDsbH98gQEBEnvxEJfjROZjyhv_FQvjIO-KEI9IEXLOLuDDXBZ3WdCqeZoZ1x8l-CUE5EXtwY4ezaoEL2W-4YRzQkXA3olvQt0bc3nkHpLss7ONgRqvUXeO_jkCq_PQXE6jdoprD1e1t7q8vjeBSJiDzkH3b5qlY4eRH2NqyjrlFt5Ve0eC2vs27TPXwJnh-kg_qd-4sQrRRM8EY-WbMXnF3UPeuqQnnakHGvOf0tyHTo8U3PmwiHkCKu7Z6F3Ux6sQ6V_-g6aeLHROO1JtgbQbae0ZthGlSWrQE4BtZVh1b8bkLu_MyCHILYM0fmyW7J3aAjjgXXf9c4cwBBXATSlrlHprhPco3eHTN8CTWnKo4OZxf744wsZ8goe2oMJeP7O1QIE241esCuSR6JnW62FnG41TQh9lTQolg8j4gqzgUV_WRt7pIY32LkP_SB24ycwvZJRnDQ91z7V-TAqh_aMb79G2UrB4gdSvYXzhKSknNv-skImVnDLCZN7Fffqd3q7zo7q8RdaN_aXWTjE5WKKhZOSnW2JfOYeZ5BOmAXSOeDA0enAFLZsspCWfSusco4Wbpi-mcW0RmGhMea4SlV68nxdRX0MgKT13le6P0V4su_yh6-m-BGvntI-KzZnTz-iOyHEwk-Signy19xIT-EHOx5q6443g-k3aZuTMzB7YoemD2uuEjxDeAls_prOqmBCMCGwAOItx5m7yjfNDsBjdn9fkMfbHH_JlgfjEKl5h75VZEicu3q6P3Ynns-fMwX_O5tS9RnWkLH4cBfiXkCBxnQyUUebE5HyUibEHPfwOvJZamvU3SclsfAnNvw5nd-Chz31Ys94WOuTx0jVcHSQc2e9i_jJEap0cIeBFm0ee_4FsdJScgdhTr0j5YGdb3owZB-3XpDIqYZUz0zrkFCxpU0tWyFIfieI-irqjLvc6S8jNYJo9LawlkH272swJER4FD0D_wVsBFq0A5g2wJU6MBBKO3TMj3Saoopg-aw0UtSu8JYzHmUcmvPKReUBNJmYtWfKg_f8sY50X0e8Op9L_BBzsBTQDv3BVS0GQ2Ps7BxOp0eG_G_MR-zfQeS3AJuhoXJWA0jZzMS9gc8PsNE7X9KBEc5MMBBjQ7le9sJyQEpx81r84HIrUBmcGvfmxgXeEkX21X81s7mvxzJ_EGl7vfMVVvP_AKV_qxtlzUbMyuGoS7lOqlrmhd3HEpFwhE7RVQtKtMgEOk7WlpmAiDeMCH04jJj9mhe5NnU5BEpoAiJAPx0nJXjkZHp9KsiwQ927njf9jW2z2z31hn3nnxXMDNrlUeS2CQ529EZHtgIIvH1We6fyK9VDgVCL_krkYGs_QfwLL8KILp91OL0f_omwzmK7ru2Fqp6oeMeYGqUvIzKqNzFNdail4stnm605iYuY7q83SBTEAmlRH7UHAzHlVCOXBa7DUz1kvUwmJIE_5nEybRLhaYbA8laEjTs2SCn4Q6R7yNtvgaTU6_aGaU4LI9dfnTG7xOthDEyUN51Y50Pi1LEC6Q4s1ixnnMuYzeqJ_BSVMN9g_bKOjnr3Uujb42KSoqTlPW8PYdA8BlZkDsito0WRuSe5fnpbV5YI6hVhmU12Oih-1WGsDNlAYp6TEPhIVpPPXS_oN2be55p6KOFvOSQu6p3JK0atsKbGelz-gcdltfQG4vYkV_EaTVBUg-pa86PMpa3EDtjsLiUtQbO1uPkscmbEcSR18YE0huJkheBVuOzZ0xJ3e8jYiCIeyrCWptzCyjt7en2-A0X-uds5R9lB4nPRC1rM4R5PJw-6IbYmz5YMmpnxtBzhuf6iy1cUnIXqBF5eLULqX0jwKK9QZPHwPl1S7ZFUfnJHqCfyGRyKUaomKWrsJ0sWOgskw3koGafYdHJ6RIWpqDJ8RgHlP9ZKwFrHJjO7CG9-7_MZ97n1F0CnDvRcd5hAcsvJGkVIz-eWJ54hNdbao4uY2Syj_Ae4YS76rGR98s6FhKMaTU3uzBqL_W2e1lVcvCc9em6SRYeyzi34KsbFKR66sVT3cgHzsB5NhdK3BDMIS68-rbZ2-_NtmbAO9Ufx80K1FCmEoGduJmPkara78UnSrK2fvscvmM4CYwzly7wooa6AhGz0WWYdtNrdyR9CCTwQIems2sHlq-KGg_co6BrdE7Ot1t83pa7ESt0I8ZPWnFVkw2lc8O1Ozh22i0cti5l-cXsHzZyZfNMPvAyWEe65kNLkBZ76fbnu3OqlRUk32FywhUUrZp_PYZHe2RuSe9rk4X3MGZg3euGalM4W0QXEc1TnkUqyW0eYiuT2SKrC7uRrohPSQEKQ7l10Kp_dnWzBRQUG7Eo6UM9g3LX7IiQMwPIA7q9sulEN9BI4vYCZAautJIwfVzdnY6JYRU084pxaxZAlQ1vYBAhHMYdFXDeT-GwAtUhfhJGQCwU21O8lqfQ0wH6-OCW6ifOrKGjWCHXQmVnlJEyosik1p7lVXX5nVILGf4bvfIeAKXyo4emOhCK1EDKdz57SOMSgNhnweLl8sCQd3cKPjsEvCvjTOJdexYr_6s7m8nb2n7FJXuBc4yI6VF_pkkNZFnm3WWH_or6K_Nou_SQZZu0uNOuEnJwx98MrFi3bCYJkptpODer6CMZK437A4uG3ohySgtMg16u4PU6PyxfGnpksDbQBcQPt4-6D6O-aLQkEXXfd_63WqHTCsRI9TnTid8DxpJffFNur_Y8hLq_FqirQRGf_O3wAd8nrKuhrf_4BmEYS0gvEYx_qQsGN1jee1waKns2MlU51eTF22Tk-fh6fpcgSmnt7VHbWK7TofVqHfM6VBCoa3LY_fJcSCF8UHpraVUq2ZPdKo14tqTM9IaOkRpcqeMXogCOe8-SjKMgS2vPI70YdDmjZTQCmviA3hg5dV_4MUYVZIuUrsce7riYFL8r4Kn0ql6U-6BnH8tK9wIsqgYnjQnDo3RHvdLwjtMOa8LjK87PkEpnWJ1bRJL5OSGFsYylfVE2NGbbpHeej6AIYzoyfqwL1g_NvKY4122E-jMCAY3_u0AVJEpFvM53pmodPAdnwvbu2Zlnnr_olM8sTRnEQLjDz5DXHjxZlEKYyZYPYCe_RH70vxcgecDwKhmABKuDWnMT5wMKMQOeJn9qvgZ8f6fYyqPasWw8DGlU_RlSnELCh97ppQW-dDx_bpt0HJA1Nwiv6cYwnhgLlZlZHUit29AoAt0X55iH1VkCScNthsjjssBkJY7ITS_h56OxyuU0Z9GvR9fQHI0HTSIsurvhJJM00J9hGvyTbYT8msgiqEY-5GAmabWF87Zu3XU4fNl6pfqzHALY-ce0FEJSmXqsk3zd43bqOHRRhad1cAbW_Bvmtdvg7QCCUZyT9eBQmEkBHyl6so41Gvzf0_qVHu03T5pSd6tMkSKyJ2_Ag4ylh7bFNSq6gFA4mGN9yy9nsNvzor79hr8v_BQ9ngAbOOVJqUXobM_vq0Z7cGra0DF0PDlDn54W1PUqyJUgprtDqJZnyIe7yqu7b0HbsRRB4yZrIrAOtMktKRnGy26FuES1x819SbRAUhZjGG1jTW5Dn3aC-AbnQkODWhNA6aPiW48R7iUR6FsF219PWFxQH0ScELls2YLxPpOtCVckUVgqXo626En4XRgpKpZIHUw9XsFiDpfhlyOYWhWldzOyy0sojdH7kPlp37Xojcd7ZCLBg9mhM90ag7pchbg0xfrX7gvx3mbrXtPrjSE44ZSSDLrr2BIbmuqYo3QlKWCu_2KpgA7CGOD9VPuLvjccWTCvo1S8oVqBcyCutoDntZuvugRz6KpZVW165oaCPV6284ec1fBtxN3ZJicVmX6W6mfH6cpn58aJSNMIx2uHP9sP0kGDp2t-E0pdGc5mjLtqYGbUSzHuJZNSxQF79NwvEl2DgdcKFMTZB1KpxrZvZ1h2B5RJZ3dYhJHstyBqYivhmAPM-fkWGyGUrsH-yvOGrDYz-oFcCjP-eabmlFVsJH7mYE4CyJKi81j429n2tuIVioik3uKeR68fkVSowQ4uosbQVHzXnL4XIyhrbWP5SD-3qZ4f_m5pv7APUnL9A3YG2GxDQJepWFEfZdydu1_AaJv64jM2Nmnz17bPLz1FIAd7E3yi8EjFKsQPPjwTlaXg0pyedIL0S6hjPZo4aPNglBmwGLNGdnI8iHt3Uy6SDkt94ran6VrJJPOswGSbg_ICRhoawcF1joc2e_Vbd35TYcnv7-wW97UI7M3pDb5OcouZrXyNbek8QdGdXzZBdnYD4ZyUFtd4j1SA80Foq8lov0nWUgEhnwiRJppp-6Ii3fC57daC7Q2FueuY5Lo9aK0cpzJixuLY4nU_qkKO_2FUkY-RHdi3abjJdlLlWCD8qkixKxctHx5Mv4_lrhLxv7lurT-laUKp53Shit2Km9OLy521FGvCJ9k88x3xowvfHg7aU1s64pJcjymPwOfPKX-LzI48QkD-MEa3HT2LUl0CiykT2hvy48cjgJAPyK6JLnc6O0clI2DI2kEsT2PL3oVndlEXxOswimEkUELGNXnQMbNL-a0oVNuetYnC15TWKJ3T6DrEcA94j4FRxAOV11xgZy7BYrMQALbGk7zMoOhBpj3ZDUFxPXYbxZGVza2b1rGfz_-i3IYqmc4OLiX677A2AhKAZ2z1cku3683aQYCV3Rp7e3oIOjjT7q0qXANFZpCPEi1X0BKQ-hHJVGQZdzqnpO3MSf6rHkb8CX5qugvfNIBLDF1kjbh2j27WouzimRgAc8kGmu13xnPqNvv-bcQZV4q0fqj34pYAT6xf_AWFwZChu0bQjK37LcjJPUvqLLI36shEcmFwoECDv5KJbxxjmPbdUrjBCOFdcE-gvSHAZakFB_QAvIfqfwrH0l4w4kXaobCqIhH-AkSCowtz7bAUzatPJxybi4NtMP7epqoJ5q_22gq3c71bDCpCKCUvhxltK0elGXtRD8WHn-fNTZmTVs-jlgmm_4kIyEFjVejhsRO1q4cYa08GKorZ0iOt2-02BnaWVWBN8bVoisFt-hA8a1bpIEL2hf36QjnX5kTTmbljkmLFZt1sRa2I0fkpI-BFj99AE2WQS72vPZaougrwJgdxPnShoUwIXV8I557x9sedflTmbnY2O4X0y5eHcCuhyvKuWZmf2EOFAOmNEi34SK2sReJjwlP5ICDno9ldPWRdHo52poqX1YIDXHypn6732E0eYEFmnopZX8VmI0JPaf8VxHfDAgqTdGkoRpnsTg97fd27ZInrCsggwGkcJX2b2pmWaXa8C4fmO1O8F5TABY4xVG5PYKPNZvWMb2DCWMi0RCEoVRydM047Bgba57LCvHcqGoYuIKcDKHOegA5SNzOHnWo34wT9mtoqoXfYnRSjZmnCCFmmTgZtnkmv1gmmYKZbxhhzzIfBPKQcXO9t1ZcAfVxbms5vXcsDghV8iXYMmMzzKovZr19vRij0pcU5tklMNpX-lkWLRN2qoSWPqR1RU8rz1yFJfrA0WvFNypfSRDreAAy3hO5Z8Ix5OGJSw8kuBN8GrfNnY5WMyZjX8gPenigQ_KlaAh6SO1ahgnkl3nGP2n5aOy5FcHqRVpfgmqsZ2NH_wE7kBRsm41xwlqjBbpaFDrSuUdNXq3xe-gjY45lVxLwzjZy1qM-r7QTBkO7j36_jaXfmgVCZdDJ3CAHiwrcmnwGeHfCq0qPgx0PuGa5VYGt2z6sWn041xxxokO6I5iCimRBh5MTXCKpNgktRuPyAVAk-kGkhTZWxc-wIDuapqqlsvsNsLUbLQU_vGudwyLdmPeg6PUkoZ_oG4qHhzHqUHZBP0m7tdqE1ZyQnIWotzSaRWTFtVP8WqTEwMVPKu_Q9yxnPQ-R87yc2wTDeMl2fh5ksCty7gaaXoQAyVLoC881WMYUW9wG-w1F7Ll7UDzdBA1sSXjGsfeybxJSz52JkmjPtKKjtxQIlecTIXEr0PWRdUMAHXnieYcwoYfq6nsKZ3R2o2gwG8_Vh3HOgk6RaXvJAANFvOQDb6PH3Ph4ol1hNaU51NfEPKYE8RiRKMsrwQAu39ybFmwAS-PHPfyTbJbc3LbCXrimLaPpcc1Ai825eJyJ3P-2Q3oBuZ5OBL1q8c4TvBP5_OjCPlfmyn1KGwbD3G_S4ZraOPYOTabFudu3u8ZzoygP5m5NLLXKxcaNxYlBwHxHOx6ciHX_03_yaWtB83_0hN2C8u9-pzl0phzb06w0XYnoa0JmbxJmYenp4s0Wscq4vvzpJXvcolNLeNWaYs-DaClSdf12lM430mTtXmYVgXVbV7ISal0JbCzvuJCAXc0FjMERdZ0X63GkJP7jkaoUjzdZigGjZvgiosEPxJXyCzr8KKk7JK4A3lqxBhEAND1oU6NtUbvkMMvdXnggbrmbSMZRqcBXf3WFrYJcJ-6ahsBYuA3lg1KBW0pmH6e8QfAjv0xangLWhBQMxsp3mmapmV5EE7PVN5R8hjSJh9sTmLXoza68UQCIctpzsXFj0TXCzq2h0Rnzv91vwEt8CIvgNq8gojtnmW3QpahugDtyN2UHm3iSiUKKwSiBZkf8ZcENLpMkVgD9IAsiTXUv_4FogWPpwAdl4zy6sL2s_ftLPmS0DmOmXRHJ9G-dE0zkMyzMqVkq7ro2B7LwfrcnZiBZi6VQej89XUmXyGcX77uFhHd_j6OWmexvu5tndGIbOTuQX0CWz9yaXU-HTJhiY9e_crNGZXi4ih_rIv92TMZivQnh5kibu8NE2nFxjpdNLpEbjDdd8PtEvAXAEE7qnFXGwGLmiSlhWDN20xWmbVLtzhLuLJxS1hIo2YpOH_4a7KS_EGZfH82vyJDh7X8eB4bN5ROW4P_izj9KFTFviX4Uo5Tu6uLexgHnao31Neb4X-i3qLOCUfKHJJlHV2Xd4Z7PRRAmC6Jh85KG12uOfi-8wZXXcg3VECVTWqFPyNC7c9NqzmqImfot_kI9r4RsxW-QGNwnFsrKc0Keljk8A-oFxXNQDOwLRsuMmDdw-f-UPrzqr9EpLrYya_wVc_idKX3Ey4ovtUf5PO8o2MXdJByG29lJT5K94vz5mAfaIxPGU2YHDcPx8MEiAayTRPd9ilSFJGeExDpt1qEXj6zgE54feCN00bl_Mj8_KrxhpC0xEipenwwi43y08gBKqnQoFrSVOcyQkGSTKPRzlmelIpOxDbPp-3hdBTTMPN5mZCDC7ACxO2CmJXwFU_m87w2ELhVx4Rn4rSCIKT8jslAicWFLMWR_Zb98JgeUs3DYyfzPeBtZ1BIKKE5MKmEyITeLXhlttU85a6y-L53Uv_QygXPMlt0J42xqXeIrHOXgGwxolXy5gOB9yjVlb_q5m1UNEGZWfqK6LvAE-J8oOACY4euLX3EWcsh0auULJi4wH3Y3nKG7HJFQyUO0JnjQwfyWfzSvelIZ41fi2Nw5r-wNqybt7tAMbUZIfcq7n_jQJscL00BxN5N-o3fEC5et1wnmQMiqISSW55c62rrN7TTeK7e6MbllJ7Co04KH-MDC7XBr6vsXmOfXXsD7izwC4YiQnOs_B5dGJrHiWlILKMJoPm9A6MY_Ipk_-ovp73PH3Spuyqj3gbaGgEY7eju2eCKgy5xjikU4zSwJvt1rqfjRZ2GSK-KvNVZXwOlcNurfjGx4gg3gD2oH3kjnOF3ZQwKf3hHyrwwoof0HQ_NKqO3hQk3elAr680JFe__PFCiN-lgyE16nSaI0NdaPIwf47eymU83M7Zd8vD7sHWJNnf1imqAiBLqXPWR7Rqm4gekkh701zPsJ2Iu6512sCNX-9KMFxIExfluqlNw6M0IlmQlht8-d47XGltzaA54GJFW3XEbd5zS-3HXSx1KvGzlXc64JuDZxLHUb5ZQzu1qEr005a3rGJk9uxvvl6fMXkjnSYxMRQILBXk_4jA17GYY_8-5yhS34A0bg1O7uT7wJn6DhLDOvBY6ajV_VYSOLpSpzOwWEokpS8-fGz7oPS24HbV0hJgI_HvMEkB9qPxUGdlSOQWQIIFTAtsMo2gf9J7z_edG6WZTPB-_SDpD69-tfdvhgNiM9GcnU_jjvZRehoOkRPEG9THHC3V0GTU3ZmsHD_S3kXlwFSqdsY6mZZ21nOAOLFs4gcrABwUzP3rEw-gaUP7mTUfd223y_P3KmOrIN7b5BR7PNgwdkw3Tkd55u7bTqxOahIR8MEPxojazJuGryPj1bNQRi8l5jbdGM_omNUJot420bj90n6NsoxmZoDeUWcR03IYRZjQjwqAq55c8fAwz_1-o0RlC7JWau77D_C1bw-_3olp_qE7MPVAwox2RLgEBZJ2JZs_h_bjkVS2T8e183UZV3XQqzte6E5urP0wV4aOJSyO6_niCHHNj3uFXHcaUO8jkJGmoTXBgvRYREn8S8wOFjGg9kJSPtiFQei9UHYF6lqIH7iPe5T8yeWEWsc1zZG9NF9MKosT5cZLKgF62oONemtZsljU9o8FSw4F4twnv4ySysMHZ1nGNa9f2XVLRRI_ktujhM7VAulFay_nfTdAPBU7vaizK83i1e3g2mzHvx0dKrtlfAjYtJmNkdQwFXChzSZT5KiLO80Hi1fSMPl6ggBo0dzKManVj_YBgrNd1HvzKE2JhGdRPwgNf-iU1wVgvqC1BQsY2qzimpDeLb2hIIj71DDZewcZhXTdFUyIfc_7dR5WjIsWLkpUrnFBYYqqrE3jGk2jc1LhtHcI-w3sqlRAMVnVWEKGsvHL4ECqvufWinq_lNZMtVu3ziWU2DtV03U1-LqGNwu6VkdVTLByIXhJ8qZENgeZmhmqhiC54zGbZFYg_WPtcBM_zuzHssq4VjmTyIgGgMqGUbsl6l2jdTT4nAM6BrwqWlg7AZaeNtuAWMjmtnHA2yB7r4OolmXsxgrW0JzKdneOQYyv5CwF1wo60FWCct5OqpqElJyBbqPcMhZKc6eQm1sQjO6nEJtqkvEuesAxaxmI9fWi3aVuTatLF5fRYgwWWYgYrUpe0efBvUBW0s6RKd7z3IZ7SBjKEdKMlzI3nhsIeiSk_-zWh37gLdozxCOGZ_Fp-1KXaO4A65vQJqivT-bzN9Cuq542hcBKgNTZfUe39CVO0Wg8E1DPdYbGHoobA9TSH--96VRj6cUVrCEG5icBEfqeylcL102XjlLoJw5HDe5QBnc8nPYVnH47WGHX2nUQdEZnoKyyRG3IR3XSWXzLmaFeod3hPeJx4xxmAFRs3-a-36lBc9FrsjMSdOULSwsQ0g7pC7J6hcxL7u5FKDtVJnM0aWHQqr93nPeOnrYo0UWSL3C8U_57xMqYm_HvOMNvEukk6q5N_NSZGt06RHVqswDL7dpK3yF0QStH8K_FoCOaHR-lOs-r2XJkxJ_9q9n22sTsAls0wObpRkI7Sgf_UxQFaLXqTaq0hnNUCOJuZdXhT2z8cg3eqAJzWC2eAkgbkr556fDnvJj6agVS8DgOfs0RwT7qORNwaIrJqr--xQACXLnaqfoOWn66Hxh4IoZ4Z0fmFcxJqgiivgp7JzJoxpq0e3V8gq5iPf3dpjbOyKxmFg9rPcOO2vWG8z8K4tqXrfMX-5k-V-7Ne7pE4XCVFdZzKFsr_JjlAidEwFMJD0KVhlrzzwJlM_MUp-I3kSR6pz484YVbnYu7_yUeBTZdasu7JU_jXEMZ38JRf2J2OXJAF5PQKZbKwk24bT3qXDjW8pfEJ-S56eepnRRYkwmKmxO1jFx8mOu61vcnfNQQ07eXq4CGwFXTICLuCfivmIn6XRX29zo8ggxcYyG39_NQJM03J8MicF7PJw8HfbHiNxdI_Z5fHuQEsFlDJrFB1KMdOoKAjFSfnSLayKiR--m9htw1Aa8M7SygithpWJ1eVFPsaG85baIZbWkJhku4x92qCAQ-9HrM_1CX_Y_PjEPqQIn-ZXcLqHDP7gVZzE7IOzYYjrGY0wfavJo9aPqu83zevqDgPovSiIHW7Vdhlrn5zEx6gpIGjcbGLdDv22GS4XC8DDpgrP6lzHURj2_TWDzBkZUgpgV12i1acosog3y_4bmodc38THXF0pusaYKuYn9Y3Ml37siLnI6DzCJjnN39kNQIuSVzDxEt-SALey0_XDpdaRtc4lK3yyZIpf2RECmW4PgeLrZqIeroDNV9D9NKcvnkW96mXr-lvthFC4RWmBVzdjKjKIVZaK0kiy8VowJ_KDoORt-pbz10a_V_Y6B8ZxK8eRg3jL2phwNIRaPiRy9RAG52KAN7OCmnG2w9__-o17aLIrGbEB-OI1tnmkeZA3kMTpw1Ab3Ml5OarPDVn29QhxJ1UxmNx-ae_Ar3NP1g9DFrc-Jy9Jug0buIOCXLcUzkN6mUf2wI3mOAo7c2qXjamZ04VElpFhizTVF0g9w2leui8KynaAW64Osk7MnMCTQ15WPMjYvCWld1RMxJ8DKqAAPqt6iwf9QP6JxOqYdtK1dyDgMAC8JUd-yXYLsKIyQudJFKOm1HUB6se_JXzHXAktSylYHrpoKujM8Mln9zAUTqOWckKBjA4BubfrWQo0iK9hFygse9dJnS_n2Om2eO8YFyjcXNLEhDoBLNrOrcw_WVXuxnqRnX1hpzj8oRfoUTbc_xtxtYGvA0ok0Bb56BNxwstYy-TUbc2-UTeIm0Sn69kWaavyP6hEqZ7QN_9eUkNoMExsyz3nrjYEbsZkrXn-2vBoWEIA11jHIm0ijR_H55BiQL0zP0I8-5bA0XXj5fVvM8QL6HGyNfpWQ_1rPiZZ3xXTcy6Ca5-QzI-voSTFnBxoPJ8tsOoKiqV9rQuUpEAAmF4KzDOOZqdqEsy_NBsDPSOlOgye-AbsJ2o7aq8HB4hmCy6rGclTNYg4pefIwX_SyA0zFYperLYjCe1hX0XjAB99uGAbWm7yBtwnQHqWybX5caNCNdtRffH6Gm3-VvKMS2FWxxcKu_WU1a4Yz969JQW8feGiFMwr0pw9v8Bn_l-_wogkp1G7I7MSn344ic-33AXpI3kkvavjJy5vwoXtm2OEE0DPZuXK8RfbV19b-8kM2KTNXqNY6E6oWy0XKN-p4EvVOY2nZODROINLUFT8thGM1ifiJun11tIMltFNEvlUfqQgugC86dH_-I4kapkCNj1DCmLVKZ8GNHDblVQYP8KlMpAMerpAfvufGUlWFBJk2g9cBRsA1-sdyZOkYo5QziEIa3iC883G2H1iFYV_WTZeQ7F-SeEZ-Edv0weZA-7Ar2KAp9_yoj1E0WlY8tc81P4eraL37Z09XdANTjazYhuQPhLcw3FcAobkdJjNX7Vvivs0VySjTYvhZtX62mFDRM4YpiXtMfCnpO4SdT7w6qm8Roj0Jwdb-y9OWJzPPZ9hV8i9bquKhJzutHSLwOqYQ_VaKZg8cHWuHoyH3LreuYWIYojhuCLKFTgRVpLB4S92Yg5jG8VT4FG1gCR-w1_CkoBXoZPYH2HLVL0nNvdPdvdOJVbo0ql_7sh69uLmJeIkBhGZqQDSmPpcDyePG5jS3XzM8LjSLH-ftCI-OV8bjviToFR_ibmGlf6B5KkdMHW1jf7x76-FYm83AoS8YBrybQ4LHafz8ndZB8rAJPAF3lRuvJd41sep8-Um2wsTbryvNJ16kQ3JhLZHddrkXjDnSCbjO7O9oFLDRgu8x3FMPBJaZynxQ8_GkBNQapo0-xNFr7eU7uNdoj2ecIc3kVVLbi55g7zWABvRsBiFb1GdVIDQNLHIHXXyK0P4QupL7wOxCB_s3109Ojvwt-WG05Dbb382bsPU5rCdeoo6OCw2g-4ZyGUUtyAcWWK4-Ul1BgePiVd8x2DwfqNkLi4EUlr-Qo_m5Zvjfa5xrkg1MgTnq709orf3QP6E2sNMc8zcu0GMrLcZcGN7CWavHF0TaGiQ8krMypphul5AaWCsW5s60d7IcbmD_1vswLFcXusL7egt9_Lf6p5UjAApFOSRvTbvhUb3OuQcbzR1CzAqsI_LWBJQv2GAvCw1Fsd-8sHVI3Y7aycr7gM6ozKJ-gA7Rs1Jq-D9X5iAmcPzDjU6xsRcav5R4BnaNqs53gaxDLiA2VIlASKTMGVfdTS2apxODxquKq7OSurKIpC4vCnKmNQZ-t7aQ_tgoNQKVEHNLgAANnLx8mIk--HMepS1OoyRcun5UL6szBsx0OuxdGVWuYyb4BEKn6quHDeMdJN70x_8Kx9HnSXn2_aOPrw4R_1oYsR-d7IpwyPf8xWVcn9zLNWIjFgeAKcQ-CbfbRdmsiQ9OI_y5Q2gbw-vi4FbGXNl01b3Rlb8_aBLxT1eldmfpl6zGqIopNRrvsLyyJRl8jKU1lzwcEEo2NqbG9ud9JRyRjpQh7TedGqnuGeOzPbBULsngnofCrXVgZvGQLtooFM4S8SSPhIczzGk6ud7xI939ubmBC8L7rvD-GDpbq8fjmkl4mSmQqoVUWyAjCUloTZb6tm67vJPjJyRc_VMvjpv08ZP8XN-DRbULF9u9gmhiinbG-FLvH2tSIuX2zNG9tqzRGLK9fPneMqtGu_Ljb4AXAoCWQSfE2tLRWkHdsBx9xkzRGuQKEi5a8MrDIGxQl91a5Vga7_R-wegPQyQQJy9ruSuC0YpTipPBwsY_rcUDbYwkx9yIO4SgsWQXoBvUBA7jGKKAgaAfhRJllN89HSn4shGWIe2lU6--pIeaOjgRzjWJGPue5RWoOCG6LZljMmD_DIN255Meiv_W3wRkpw4nChq2sXuc5bnvo_9Lo_hVqvYQCo9pztvMAaiobaeS9R01YRTF4s7gZjnQWP_2Z7ugm8tm9FrOYb9aXIQTmP9VyaRtAUrTuGWcOsfKUX9_qtrmdWVNqnLGIVJCllOenmj2TajL98s8DeZdZn7quADgwN5_bxRbMfZ5yspQwij4wH-fWYqM6YXRxxGP6ElL0uhwRvIgekUGOdYPz71lftA-0ax9Kxjlk2pJ5ynJyl-YO_aIwp-NzPWWw9Y5yuwEWWN3HXq7C2jJVSAhJ-X497mhaxIfYXkC_N_QC3B4kht8WHDdJf9VzkZlaxTWib6_tEc9hPb6Q4yrMishu2bUaSE6_HPDZQan0XsbYiPhcFS1OfYZbzLGmlJQ6B3f6tThTG8eU4h64hn2FCv9KzfPdDcbv_FbeZCMPfFSAeFcicwBiFLQ8ckRnQ-riW3LNt2Q6mS_2oW2-VPcOD4b4FCXVlkfdXsvuFCUZImWbty81lBkotIyiQPwQX8d4D7U",{"type":374,"children":1021,"toc":1030},[1022,1026],{"type":377,"tag":422,"props":1023,"children":1024},{},[1025],{"type":386,"value":1015},{"type":377,"tag":1027,"props":1028,"children":1029},"hr",{},[],{"title":369,"searchDepth":736,"depth":736,"links":1031},[],"content:notes-to-self:what-god-quantum-mechanics-and-consciousness-have-in-common.md","notes-to-self/what-god-quantum-mechanics-and-consciousness-have-in-common.md","notes-to-self/what-god-quantum-mechanics-and-consciousness-have-in-common",{"_path":1036,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":362,"description":1037,"slug":363,"date":1038,"dateString":1039,"encrypted":368,"encryptedBody":372,"body":1040,"_type":742,"_id":1081,"_source":744,"_file":1082,"_stem":1083,"_extension":747},"/notes-to-self/you-are-h","You are having a hard time making any model that looks good rendered. You had the best luck with a blender metallic texture with a random rusty aircraft carrier image. You had a dream of not having to do custom textures — of modeling so big parts could just be metal and details would be separate polygons matched to some greeble texture. Have not found success there.",1721318400000,"2024.07.18",{"type":374,"children":1041,"toc":1079},[1042,1046,1051,1056,1065,1074],{"type":377,"tag":422,"props":1043,"children":1044},{},[1045],{"type":386,"value":1037},{"type":377,"tag":422,"props":1047,"children":1048},{},[1049],{"type":386,"value":1050},"Maybe your base texture is not good. Should you be able to make a cube that looks like a real metal object hanging in space? What’s the secret to that?",{"type":377,"tag":422,"props":1052,"children":1053},{},[1054],{"type":386,"value":1055},"PBR = “Physically Based Rendering”. “A PBR texture is just a set of images for albedo, metal/specular, roughness, normal, displacement, ao, emission, to feed to a PBR shader.”",{"type":377,"tag":422,"props":1057,"children":1058},{},[1059],{"type":377,"tag":434,"props":1060,"children":1063},{"href":1061,"rel":1062},"https://polyhaven.com/textures/",[438],[1064],{"type":386,"value":1061},{"type":377,"tag":422,"props":1066,"children":1067},{},[1068],{"type":377,"tag":434,"props":1069,"children":1072},{"href":1070,"rel":1071},"https://quixel.com/megascans",[438],[1073],{"type":386,"value":1070},{"type":377,"tag":422,"props":1075,"children":1076},{},[1077],{"type":386,"value":1078},"Adobe Substance is the de facto standard tool for texturing and other fanciness. Non-subscription version can be purchased on Steam for $200.",{"title":369,"searchDepth":736,"depth":736,"links":1080},[],"content:notes-to-self:you-are-h.md","notes-to-self/you-are-h.md","notes-to-self/you-are-h",{"_path":1085,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":38,"description":1086,"slug":39,"date":1087,"dateString":1088,"encrypted":368,"encryptedBody":372,"body":1089,"_type":742,"_id":1126,"_source":744,"_file":1127,"_stem":1128,"_extension":747},"/notes-to-self/blender","You are bad at modeling, and want to get better (to make spaceships). Added difficulty of your end game being use for real time rendering, requires simpler models.",1719158400000,"2024.06.23",{"type":374,"children":1090,"toc":1124},[1091,1095,1100,1113],{"type":377,"tag":422,"props":1092,"children":1093},{},[1094],{"type":386,"value":1086},{"type":377,"tag":422,"props":1096,"children":1097},{},[1098],{"type":386,"value":1099},"Your approach is to make many many bad models until you get good. What you’ve learned:",{"type":377,"tag":378,"props":1101,"children":1102},{},[1103,1108],{"type":377,"tag":382,"props":1104,"children":1105},{},[1106],{"type":386,"value":1107},"Use bool tool add on (free) in Blender. Use “Brush Boolean” to make non-destructive changes.",{"type":377,"tag":382,"props":1109,"children":1110},{},[1111],{"type":386,"value":1112},"Use bevel modifier to make basic shapes look less basic.",{"type":377,"tag":422,"props":1114,"children":1115},{},[1116,1118],{"type":386,"value":1117},"This very fast video put you on to bool tool and touches on edges for making manageable UV maps: ",{"type":377,"tag":434,"props":1119,"children":1122},{"href":1120,"rel":1121},"https://www.youtube.com/watch?v=zit7UmzcSgU",[438],[1123],{"type":386,"value":1120},{"title":369,"searchDepth":736,"depth":736,"links":1125},[],"content:notes-to-self:blender.md","notes-to-self/blender.md","notes-to-self/blender",{"_path":1130,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":176,"description":369,"slug":177,"date":1131,"dateString":1132,"encrypted":368,"encryptedBody":372,"body":1133,"_type":742,"_id":1314,"_source":744,"_file":1315,"_stem":1316,"_extension":747},"/notes-to-self/military-ranks",1713801600000,"2024.04.22",{"type":374,"children":1134,"toc":1312},[1135],{"type":377,"tag":1136,"props":1137,"children":1138},"table",{},[1139,1163],{"type":377,"tag":1140,"props":1141,"children":1142},"thead",{},[1143],{"type":377,"tag":1144,"props":1145,"children":1146},"tr",{},[1147,1153,1158],{"type":377,"tag":1148,"props":1149,"children":1150},"th",{},[1151],{"type":386,"value":1152},"Unit Name",{"type":377,"tag":1148,"props":1154,"children":1155},{},[1156],{"type":386,"value":1157},"Size",{"type":377,"tag":1148,"props":1159,"children":1160},{},[1161],{"type":386,"value":1162},"Rank",{"type":377,"tag":1164,"props":1165,"children":1166},"tbody",{},[1167,1186,1204,1222,1240,1258,1276,1294],{"type":377,"tag":1144,"props":1168,"children":1169},{},[1170,1176,1181],{"type":377,"tag":1171,"props":1172,"children":1173},"td",{},[1174],{"type":386,"value":1175},"Squad",{"type":377,"tag":1171,"props":1177,"children":1178},{},[1179],{"type":386,"value":1180},"6-10 Soldiers",{"type":377,"tag":1171,"props":1182,"children":1183},{},[1184],{"type":386,"value":1185},"Sergeant",{"type":377,"tag":1144,"props":1187,"children":1188},{},[1189,1194,1199],{"type":377,"tag":1171,"props":1190,"children":1191},{},[1192],{"type":386,"value":1193},"Platoon",{"type":377,"tag":1171,"props":1195,"children":1196},{},[1197],{"type":386,"value":1198},"3-4 Squads",{"type":377,"tag":1171,"props":1200,"children":1201},{},[1202],{"type":386,"value":1203},"2nd Lieutenant",{"type":377,"tag":1144,"props":1205,"children":1206},{},[1207,1212,1217],{"type":377,"tag":1171,"props":1208,"children":1209},{},[1210],{"type":386,"value":1211},"Company/Battery/Troop",{"type":377,"tag":1171,"props":1213,"children":1214},{},[1215],{"type":386,"value":1216},"3-4 Platoons",{"type":377,"tag":1171,"props":1218,"children":1219},{},[1220],{"type":386,"value":1221},"Captain/1st Lieutenant/Major",{"type":377,"tag":1144,"props":1223,"children":1224},{},[1225,1230,1235],{"type":377,"tag":1171,"props":1226,"children":1227},{},[1228],{"type":386,"value":1229},"Battalion",{"type":377,"tag":1171,"props":1231,"children":1232},{},[1233],{"type":386,"value":1234},"3-5 Companies",{"type":377,"tag":1171,"props":1236,"children":1237},{},[1238],{"type":386,"value":1239},"Lieutenant Colonel",{"type":377,"tag":1144,"props":1241,"children":1242},{},[1243,1248,1253],{"type":377,"tag":1171,"props":1244,"children":1245},{},[1246],{"type":386,"value":1247},"Brigade/Regiment",{"type":377,"tag":1171,"props":1249,"children":1250},{},[1251],{"type":386,"value":1252},"3-5 Battalions",{"type":377,"tag":1171,"props":1254,"children":1255},{},[1256],{"type":386,"value":1257},"Brigadier General/Colonel",{"type":377,"tag":1144,"props":1259,"children":1260},{},[1261,1266,1271],{"type":377,"tag":1171,"props":1262,"children":1263},{},[1264],{"type":386,"value":1265},"Division",{"type":377,"tag":1171,"props":1267,"children":1268},{},[1269],{"type":386,"value":1270},"3 Brigades",{"type":377,"tag":1171,"props":1272,"children":1273},{},[1274],{"type":386,"value":1275},"Major General (2 stars)",{"type":377,"tag":1144,"props":1277,"children":1278},{},[1279,1284,1289],{"type":377,"tag":1171,"props":1280,"children":1281},{},[1282],{"type":386,"value":1283},"Corps",{"type":377,"tag":1171,"props":1285,"children":1286},{},[1287],{"type":386,"value":1288},"2+ Divisions",{"type":377,"tag":1171,"props":1290,"children":1291},{},[1292],{"type":386,"value":1293},"Lieutenant General (3 stars)",{"type":377,"tag":1144,"props":1295,"children":1296},{},[1297,1302,1307],{"type":377,"tag":1171,"props":1298,"children":1299},{},[1300],{"type":386,"value":1301},"Field Army",{"type":377,"tag":1171,"props":1303,"children":1304},{},[1305],{"type":386,"value":1306},"50K+ Soldiers",{"type":377,"tag":1171,"props":1308,"children":1309},{},[1310],{"type":386,"value":1311},"General (4 stars)",{"title":369,"searchDepth":736,"depth":736,"links":1313},[],"content:notes-to-self:military-ranks.md","notes-to-self/military-ranks.md","notes-to-self/military-ranks",{"_path":1318,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":293,"description":1319,"slug":294,"date":1320,"dateString":1321,"encrypted":368,"encryptedBody":372,"body":1322,"_type":742,"_id":1593,"_source":744,"_file":1594,"_stem":1595,"_extension":747},"/notes-to-self/supabase","Experimentally using for playkode.com reboot.",1713715200000,"2024.04.21",{"type":374,"children":1323,"toc":1589},[1324,1328,1333,1366,1371,1394,1399,1404,1416,1422,1428,1433,1438,1449,1455,1472,1477,1488,1493,1502,1507,1516,1521,1530,1536,1570,1576],{"type":377,"tag":422,"props":1325,"children":1326},{},[1327],{"type":386,"value":1319},{"type":377,"tag":422,"props":1329,"children":1330},{},[1331],{"type":386,"value":1332},"Free tier has",{"type":377,"tag":378,"props":1334,"children":1335},{},[1336,1341,1346,1351,1356,1361],{"type":377,"tag":382,"props":1337,"children":1338},{},[1339],{"type":386,"value":1340},"unlimited API calls",{"type":377,"tag":382,"props":1342,"children":1343},{},[1344],{"type":386,"value":1345},"50K monthly active users",{"type":377,"tag":382,"props":1347,"children":1348},{},[1349],{"type":386,"value":1350},"500MB DB space",{"type":377,"tag":382,"props":1352,"children":1353},{},[1354],{"type":386,"value":1355},"5GB Bandwidth",{"type":377,"tag":382,"props":1357,"children":1358},{},[1359],{"type":386,"value":1360},"1GB File storage",{"type":377,"tag":382,"props":1362,"children":1363},{},[1364],{"type":386,"value":1365},"2 active projects at a time",{"type":377,"tag":422,"props":1367,"children":1368},{},[1369],{"type":386,"value":1370},"Has",{"type":377,"tag":378,"props":1372,"children":1373},{},[1374,1379,1384,1389],{"type":377,"tag":382,"props":1375,"children":1376},{},[1377],{"type":386,"value":1378},"Authentication",{"type":377,"tag":382,"props":1380,"children":1381},{},[1382],{"type":386,"value":1383},"Postgres",{"type":377,"tag":382,"props":1385,"children":1386},{},[1387],{"type":386,"value":1388},"File storage",{"type":377,"tag":382,"props":1390,"children":1391},{},[1392],{"type":386,"value":1393},"Cloud functions",{"type":377,"tag":422,"props":1395,"children":1396},{},[1397],{"type":386,"value":1398},"Client can basically query Postgres, with both row-level and column-level auth possible. That’s great.",{"type":377,"tag":422,"props":1400,"children":1401},{},[1402],{"type":386,"value":1403},"Possibly harder, more complicated API calls can be done with “edge” functions (functions in the cloud). But you are tempted to move as much logic to the client as possible, as long as data integrity doesn’t become an issue (for example, client is quit in the middle of a multi-step process). Does Supabase allow transactions? No way they’d be possible outside of an edge function?",{"type":377,"tag":422,"props":1405,"children":1406},{},[1407,1414],{"type":377,"tag":434,"props":1408,"children":1411},{"href":1409,"rel":1410},"https://stackoverflow.com/a/77052403",[438],[1412],{"type":386,"value":1413},"Stackflow answer",{"type":386,"value":1415}," suggests Postgres function or trigger.",{"type":377,"tag":654,"props":1417,"children":1419},{"id":1418},"snippets-of-interest",[1420],{"type":386,"value":1421},"Snippets of Interest",{"type":377,"tag":632,"props":1423,"children":1425},{"id":1424},"to-manage-auth-policy-with-indirect-ownership",[1426],{"type":386,"value":1427},"To Manage Auth Policy with Indirect Ownership?",{"type":377,"tag":422,"props":1429,"children":1430},{},[1431],{"type":386,"value":1432},"In my case, a user has many projects. A project has many codes. How to know if a code can be updated by user?",{"type":377,"tag":422,"props":1434,"children":1435},{},[1436],{"type":386,"value":1437},"Auth policy for UPDATE looks like:",{"type":377,"tag":587,"props":1439,"children":1444},{"className":1440,"code":1442,"language":1443,"meta":369},[1441],"language-sql","create policy \"Update code in projects user owns\"\n  on \"public\".\"code\"\n  as permissive for update to authenticated using (\n    (( SELECT auth.uid() AS uid) IN (\n      SELECT projects.user_id FROM projects WHERE (\n          code.project_id = projects.id\n        )\n      )\n    )\n  );\n","sql",[1445],{"type":377,"tag":592,"props":1446,"children":1447},{"__ignoreMap":369},[1448],{"type":386,"value":1442},{"type":377,"tag":632,"props":1450,"children":1452},{"id":1451},"to-use-an-edge-function-from-web-client",[1453],{"type":386,"value":1454},"To Use an Edge Function From Web Client",{"type":377,"tag":422,"props":1456,"children":1457},{},[1458,1464,1466],{"type":377,"tag":434,"props":1459,"children":1462},{"href":1460,"rel":1461},"https://supabase.com/docs/guides/functions/cors",[438],[1463],{"type":386,"value":1460},{"type":386,"value":1465},"\nfor postgres: ",{"type":377,"tag":434,"props":1467,"children":1470},{"href":1468,"rel":1469},"https://supabase.com/docs/guides/functions/connect-to-postgres",[438],[1471],{"type":386,"value":1468},{"type":377,"tag":422,"props":1473,"children":1474},{},[1475],{"type":386,"value":1476},"Edge function:",{"type":377,"tag":587,"props":1478,"children":1483},{"className":1479,"code":1481,"language":1482,"meta":369},[1480],"language-ts","Deno.serve(async (req) => {\n  const corsHeaders = {\n    'Access-Control-Allow-Origin': '*',\n    'Access-Control-Allow-Headers': 'authorization, x-client-info, apikey, content-type',\n  }\n\n if (req.method === 'OPTIONS') {\n     return new Response('ok', { headers: corsHeaders })\n   }\n\n   try {\n     const { name } = await req.json()\n     const data = {\n       message: `Hello ${name}!`,\n     }\n\n     return new Response(JSON.stringify(data), {\n       headers: { ...corsHeaders, 'Content-Type': 'application/json' },\n       status: 200,\n     })\n   } catch (error) {\n     return new Response(JSON.stringify({ error: error.message }), {\n       headers: { ...corsHeaders, 'Content-Type': 'application/json' },\n       status: 400,\n     })\n   }\n})\n\n","ts",[1484],{"type":377,"tag":592,"props":1485,"children":1486},{"__ignoreMap":369},[1487],{"type":386,"value":1481},{"type":377,"tag":422,"props":1489,"children":1490},{},[1491],{"type":386,"value":1492},"Client:",{"type":377,"tag":587,"props":1494,"children":1497},{"className":1495,"code":1496,"language":1482,"meta":369},[1480],"const { data, error } = await supabase.functions.invoke('hello-world', {\n    body: { name: 'Foobar' }\n  })\n",[1498],{"type":377,"tag":592,"props":1499,"children":1500},{"__ignoreMap":369},[1501],{"type":386,"value":1496},{"type":377,"tag":422,"props":1503,"children":1504},{},[1505],{"type":386,"value":1506},"Create an edge function:",{"type":377,"tag":587,"props":1508,"children":1511},{"className":1509,"code":1510,"language":772,"meta":369},[774],"$ supabase functions new \u003Cfunction-name>\n",[1512],{"type":377,"tag":592,"props":1513,"children":1514},{"__ignoreMap":369},[1515],{"type":386,"value":1510},{"type":377,"tag":422,"props":1517,"children":1518},{},[1519],{"type":386,"value":1520},"Deploy an edge function:",{"type":377,"tag":587,"props":1522,"children":1525},{"className":1523,"code":1524,"language":772,"meta":369},[774],"$ supabase functions deploy \u003Cfunction-name>\n$ supabase functions deploy # deploys all functions\n",[1526],{"type":377,"tag":592,"props":1527,"children":1528},{"__ignoreMap":369},[1529],{"type":386,"value":1524},{"type":377,"tag":632,"props":1531,"children":1533},{"id":1532},"to-install-cli",[1534],{"type":386,"value":1535},"To Install CLI",{"type":377,"tag":422,"props":1537,"children":1538},{},[1539,1541,1547,1549,1555,1557,1563,1565],{"type":386,"value":1540},"You used ",{"type":377,"tag":592,"props":1542,"children":1544},{"className":1543},[],[1545],{"type":386,"value":1546},"go",{"type":386,"value":1548}," method (not Homebrew). Was installed in ",{"type":377,"tag":592,"props":1550,"children":1552},{"className":1551},[],[1553],{"type":386,"value":1554},"~/go/bin",{"type":386,"value":1556}," as ",{"type":377,"tag":592,"props":1558,"children":1560},{"className":1559},[],[1561],{"type":386,"value":1562},"cli",{"type":386,"value":1564}," so you renamed it to ",{"type":377,"tag":592,"props":1566,"children":1568},{"className":1567},[],[1569],{"type":386,"value":294},{"type":377,"tag":654,"props":1571,"children":1573},{"id":1572},"unanswered-questions",[1574],{"type":386,"value":1575},"Unanswered Questions",{"type":377,"tag":378,"props":1577,"children":1578},{},[1579,1584],{"type":377,"tag":382,"props":1580,"children":1581},{},[1582],{"type":386,"value":1583},"How to do database migrations? Can all this config be expressed in code & put under version control & made repeatable?",{"type":377,"tag":382,"props":1585,"children":1586},{},[1587],{"type":386,"value":1588},"Edge functions in particular; local testing? Must always be deployed individually, manually?",{"title":369,"searchDepth":736,"depth":736,"links":1590},[1591,1592],{"id":1418,"depth":739,"text":1421},{"id":1572,"depth":739,"text":1575},"content:notes-to-self:supabase.md","notes-to-self/supabase.md","notes-to-self/supabase",{"_path":1597,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":98,"description":1598,"slug":99,"date":1599,"dateString":1600,"encrypted":368,"encryptedBody":372,"body":1601,"_type":742,"_id":1654,"_source":744,"_file":1655,"_stem":1656,"_extension":747},"/notes-to-self/game-idea-lunar-lander-motherload","Also Lunar Leeper? Like Motherload in that you have to return to base to refuel between excursions. Farther and farther excursions to get (mine? collect?) better and better resources. Loses Motherload’s live-with-the-changes-you-made pleasure.",1710950400000,"2024-03-20",{"type":374,"children":1602,"toc":1651},[1603,1607,1612,1640,1646],{"type":377,"tag":422,"props":1604,"children":1605},{},[1606],{"type":386,"value":1598},{"type":377,"tag":422,"props":1608,"children":1609},{},[1610],{"type":386,"value":1611},"Ideas:",{"type":377,"tag":378,"props":1613,"children":1614},{},[1615,1620,1625,1630,1635],{"type":377,"tag":382,"props":1616,"children":1617},{},[1618],{"type":386,"value":1619},"upgrade to level an area for landing",{"type":377,"tag":382,"props":1621,"children":1622},{},[1623],{"type":386,"value":1624},"upgrade to drop a refueling way station",{"type":377,"tag":382,"props":1626,"children":1627},{},[1628],{"type":386,"value":1629},"carrying more fuel = heavier, need more thrust?",{"type":377,"tag":382,"props":1631,"children":1632},{},[1633],{"type":386,"value":1634},"more thrust = burn more fuel?",{"type":377,"tag":382,"props":1636,"children":1637},{},[1638],{"type":386,"value":1639},"upgrade to prevent tipping over (automatic stabilizer rockets?)",{"type":377,"tag":654,"props":1641,"children":1643},{"id":1642},"perverse-idea",[1644],{"type":386,"value":1645},"Perverse Idea",{"type":377,"tag":422,"props":1647,"children":1648},{},[1649],{"type":386,"value":1650},"UI test pilot. Controls to pilot become increasingly complex/obtuse as committee “improves” it. Might not be fun but might get you noticed.",{"title":369,"searchDepth":736,"depth":736,"links":1652},[1653],{"id":1642,"depth":739,"text":1645},"content:notes-to-self:game-idea-lunar-lander-motherload.md","notes-to-self/game-idea-lunar-lander-motherload.md","notes-to-self/game-idea-lunar-lander-motherload",{"_path":1658,"_dir":367,"_draft":368,"_partial":368,"_locale":369,"title":197,"description":1659,"slug":198,"date":1660,"dateString":1661,"encrypted":368,"encryptedBody":372,"body":1662,"_type":742,"_id":2528,"_source":744,"_file":2529,"_stem":2530,"_extension":747},"/notes-to-self/mystery-theater","Personal project to present interface to public domain CBS Radio Mystery Theater library. Problems:",1621958400000,"2021-05-25",{"type":374,"children":1663,"toc":2521},[1664,1668,1733,1738,1746,1751,1762,1773,1779,1792,1797,1806,1815,1821,1851,2304,2316,2321,2326,2349,2355,2368,2373,2386,2391,2404,2410,2423,2431,2484,2489,2516],{"type":377,"tag":422,"props":1665,"children":1666},{},[1667],{"type":386,"value":1659},{"type":377,"tag":671,"props":1669,"children":1670},{},[1671,1693,1705],{"type":377,"tag":382,"props":1672,"children":1673},{},[1674,1676,1683,1685,1691],{"type":386,"value":1675},"Top hit is this ",{"type":377,"tag":434,"props":1677,"children":1680},{"href":1678,"rel":1679},"https://www.cbsrmt.com",[438],[1681],{"type":386,"value":1682},"sub-optimal site",{"type":386,"value":1684}," which is ad-laden and broadly anti-user. However, operator seems protective of his work (there's a crudely-named anti-ad-block script; all audio files names start with ",{"type":377,"tag":592,"props":1686,"children":1688},{"className":1687},[],[1689],{"type":386,"value":1690},"CBSMRT.com…",{"type":386,"value":1692},"; can I ethically scrape since it's public domain?",{"type":377,"tag":382,"props":1694,"children":1695},{},[1696,1703],{"type":377,"tag":434,"props":1697,"children":1700},{"href":1698,"rel":1699},"https://www.nettally.com/keith.flowers",[438],[1701],{"type":386,"value":1702},"This separate site",{"type":386,"value":1704}," is specifically user-friendly, although quite plain — it's meant for low-vision users. Great resource to compare against #1. Different episode descriptions. No audio files.",{"type":377,"tag":382,"props":1706,"children":1707},{},[1708,1710,1717,1719,1725,1727],{"type":386,"value":1709},"Internet archive lets you download ",{"type":377,"tag":434,"props":1711,"children":1714},{"href":1712,"rel":1713},"https://ia800703.us.archive.org/view_archive.php?archive=/11/items/cbs_radio_mystery_theater/cbs_radio_mystery_theater-0001-0050.zip",[438],[1715],{"type":386,"value":1716},"for example",{"type":386,"value":1718}," but the urls may not be predictable (ia800703.us.archive.org?). However - the files sizes are smaller, and ads have been removed, at least on your random samples. cbsmrt.com claims they have some superior recordings. ",{"type":377,"tag":1720,"props":1721,"children":1722},"strong",{},[1723],{"type":386,"value":1724},"OH!",{"type":386,"value":1726}," Internet archive's actual URLs are completely usable, assuming you can hot-link to them, e.g. ",{"type":377,"tag":592,"props":1728,"children":1730},{"className":1729},[],[1731],{"type":386,"value":1732},"https://archive.org/download/cbs_radio_mystery_theater/cbs_radio_mystery_theater-0701-0750.zip/cbs_radio_mystery_theater-0701-0750%2Fcbsrmt_0749_neatness_counts.mp3",{"type":377,"tag":422,"props":1734,"children":1735},{},[1736],{"type":386,"value":1737},"You began this post actually to record how to trim MP3s on the command line. Ffmpeg can do it, and you can download a precompiled binary from ffmpeg.org. You can't snip audio out, but you can make a new audio file (without re-compressing) by taking copying just a portion of the source:",{"type":377,"tag":587,"props":1739,"children":1741},{"code":1740},"$ ./ffmpeg -i your-input.mp3 -vn -acodec copy -ss 00:00:00 -to 00:02:40 your-output.mp3\n",[1742],{"type":377,"tag":592,"props":1743,"children":1744},{"__ignoreMap":369},[1745],{"type":386,"value":1740},{"type":377,"tag":422,"props":1747,"children":1748},{},[1749],{"type":386,"value":1750},"You could take all the portions you want to keep, then concatenate them with ffmpeg.",{"type":377,"tag":422,"props":1752,"children":1753},{},[1754,1756],{"type":386,"value":1755},"Also maybe: ",{"type":377,"tag":434,"props":1757,"children":1760},{"href":1758,"rel":1759},"https://unix.stackexchange.com/questions/182602/trim-audio-file-using-start-and-stop-times",[438],[1761],{"type":386,"value":1758},{"type":377,"tag":422,"props":1763,"children":1764},{},[1765,1767],{"type":386,"value":1766},"Also: ",{"type":377,"tag":434,"props":1768,"children":1771},{"href":1769,"rel":1770},"https://askubuntu.com/questions/927308/how-to-crop-edit-mp3-files",[438],[1772],{"type":386,"value":1769},{"type":377,"tag":685,"props":1774,"children":1776},{"id":1775},"_2021-06-11",[1777],{"type":386,"value":1778},"2021-06-11",{"type":377,"tag":422,"props":1780,"children":1781},{},[1782,1784,1790],{"type":386,"value":1783},"Using ",{"type":377,"tag":592,"props":1785,"children":1787},{"className":1786},[],[1788],{"type":386,"value":1789},"\u003Ca href=\"…\" download=\"filename.mp3\">",{"type":386,"value":1791}," sometimes works and sometimes does not with archive.org. Chrome and Firefox both state that it shouldn't work for cross-origin requests - perhaps sometimes archive.org puts in the \"right\" header and sometimes it does not.",{"type":377,"tag":422,"props":1793,"children":1794},{},[1795],{"type":386,"value":1796},"A possible solution would be to download the data in the client as a blob, then save it. Idea from this MS polyfill and this SO about saving a blob:",{"type":377,"tag":422,"props":1798,"children":1799},{},[1800],{"type":377,"tag":434,"props":1801,"children":1804},{"href":1802,"rel":1803},"https://github.com/jelmerdemaat/dwnld-attr-polyfill/blob/master/src/download-polyfill.js",[438],[1805],{"type":386,"value":1802},{"type":377,"tag":422,"props":1807,"children":1808},{},[1809],{"type":377,"tag":434,"props":1810,"children":1813},{"href":1811,"rel":1812},"https://stackoverflow.com/questions/25547475/save-to-local-file-from-blob",[438],[1814],{"type":386,"value":1811},{"type":377,"tag":654,"props":1816,"children":1818},{"id":1817},"making-ad-free-version-of-an-episode",[1819],{"type":386,"value":1820},"Making Ad-free Version of an Episode",{"type":377,"tag":422,"props":1822,"children":1823},{},[1824,1826,1832,1834,1840,1842,1849],{"type":386,"value":1825},"Note: ",{"type":377,"tag":592,"props":1827,"children":1829},{"className":1828},[],[1830],{"type":386,"value":1831},"ffmpeg",{"type":386,"value":1833}," executable must be in same folder as swift script, ",{"type":377,"tag":592,"props":1835,"children":1837},{"className":1836},[],[1838],{"type":386,"value":1839},"~/Projects/web/mystery-theater-browser/tools",{"type":386,"value":1841},". You downloaded precompiled version from ",{"type":377,"tag":434,"props":1843,"children":1846},{"href":1844,"rel":1845},"https://evermeet.cx/ffmpeg/",[438],[1847],{"type":386,"value":1848},"here",{"type":386,"value":1850}," even though it's not compiled for ARM/Apple silicon. You had to manually open it from the Finder to get the \"unverified; run anyway?\" prompt before the script was allowed to run it.",{"type":377,"tag":671,"props":1852,"children":1853},{},[1854,1859,1908,1913,1918,1944,1999,2004,2009,2020,2072,2280,2291],{"type":377,"tag":382,"props":1855,"children":1856},{},[1857],{"type":386,"value":1858},"Open MP3 in Audacity",{"type":377,"tag":382,"props":1860,"children":1861},{},[1862,1864,1870,1872,1878,1880,1885,1887,1893,1895],{"type":386,"value":1863},"In Audacity, use ",{"type":377,"tag":1865,"props":1866,"children":1867},"em",{},[1868],{"type":386,"value":1869},"seek",{"type":386,"value":1871}," (Transport > Scrubbing > Seek; you assigned to ",{"type":377,"tag":592,"props":1873,"children":1875},{"className":1874},[],[1876],{"type":386,"value":1877},"S",{"type":386,"value":1879}," key) to find boundaries of commercial breaks; it will play the area around the cursor as you move it. Use ",{"type":377,"tag":1865,"props":1881,"children":1882},{},[1883],{"type":386,"value":1884},"play cut preview",{"type":386,"value":1886}," (UI unknown but has default shortcut ",{"type":377,"tag":592,"props":1888,"children":1890},{"className":1889},[],[1891],{"type":386,"value":1892},"C",{"type":386,"value":1894}," key) to play the area just before and after the selection. Unfortunately, switching between those modes clears the selection. Use Command-E to fit the view to the selection and Command-F to fit the view to the full length.",{"type":377,"tag":671,"props":1896,"children":1897},{},[1898,1903],{"type":377,"tag":382,"props":1899,"children":1900},{},[1901],{"type":386,"value":1902},"\"Acts\" are about 12 minutes long",{"type":377,"tag":382,"props":1904,"children":1905},{},[1906],{"type":386,"value":1907},"Commercial breaks are 2-3 minutes long",{"type":377,"tag":382,"props":1909,"children":1910},{},[1911],{"type":386,"value":1912},"For each break you find, hit Command-B (or Edit > Labels > Add Label at Selection). You may but are not required to type in a label.",{"type":377,"tag":382,"props":1914,"children":1915},{},[1916],{"type":386,"value":1917},"When all sections to remove have been so labeled, select File > Export > Export Labels…",{"type":377,"tag":382,"props":1919,"children":1920},{},[1921,1923,1929,1931,1937,1939],{"type":386,"value":1922},"Open a terminal window in the ",{"type":377,"tag":592,"props":1924,"children":1926},{"className":1925},[],[1927],{"type":386,"value":1928},"tools",{"type":386,"value":1930}," path of the ",{"type":377,"tag":592,"props":1932,"children":1934},{"className":1933},[],[1935],{"type":386,"value":1936},"mystery-theater-browser",{"type":386,"value":1938}," project, e.g. ",{"type":377,"tag":592,"props":1940,"children":1942},{"className":1941},[],[1943],{"type":386,"value":1839},{"type":377,"tag":382,"props":1945,"children":1946},{},[1947,1949,1957,1961,1963,1971],{"type":386,"value":1948},"Start typing a command in the terminal using the script to create the new (but not-re-encoded) MP3:",{"type":377,"tag":587,"props":1950,"children":1952},{"code":1951},"./mp3-extract.swift \u003Cepisode #> \u003Cin.mp3> \u003Cexported lables file> ...\n",[1953],{"type":377,"tag":592,"props":1954,"children":1955},{"__ignoreMap":369},[1956],{"type":386,"value":1951},{"type":377,"tag":1958,"props":1959,"children":1960},"br",{},[],{"type":386,"value":1962},"eg:",{"type":377,"tag":587,"props":1964,"children":1966},{"code":1965},"/mp3-extract.swift 57 /Volumes/Time\\ Machine/mystery-theater/cbsmrt-ken-long-collection/br/740608\\ The\\ Fall\\ Of\\ The\\ House\\ Of\\ Usher\\ WOR.mp3 /Volumes/Time\\ Machine/mystery-theater/cbsmrt-ken-long-collection/br/740608\\ The\\ Fall\\ Of\\ The\\ House\\ Of\\ Usher\\ WOR.txt\n",[1967],{"type":377,"tag":592,"props":1968,"children":1969},{"__ignoreMap":369},[1970],{"type":386,"value":1965},{"type":377,"tag":671,"props":1972,"children":1973},{},[1974,1986],{"type":377,"tag":382,"props":1975,"children":1976},{},[1977,1979,1984],{"type":386,"value":1978},"This command is for specifying the chunks to ",{"type":377,"tag":1720,"props":1980,"children":1981},{},[1982],{"type":386,"value":1983},"exclude",{"type":386,"value":1985},".",{"type":377,"tag":382,"props":1987,"children":1988},{},[1989,1991,1997],{"type":386,"value":1990},"The ",{"type":377,"tag":592,"props":1992,"children":1994},{"className":1993},[],[1995],{"type":386,"value":1996},"episode #",{"type":386,"value":1998}," is used for automatically renaming the resulting MP3.",{"type":377,"tag":382,"props":2000,"children":2001},{},[2002],{"type":386,"value":2003},"Once complete, hit return to execute the command. A new MP3 will be created in the same directory as the source MP3.",{"type":377,"tag":382,"props":2005,"children":2006},{},[2007],{"type":386,"value":2008},"Listen to the resulting recording to confirm no content has been lost. It should be around 43 to 47 minutes long.",{"type":377,"tag":382,"props":2010,"children":2011},{},[2012,2014],{"type":386,"value":2013},"Copy the resulting recording to the appropriate directory on the \"Time Machine\" external drive: ",{"type":377,"tag":592,"props":2015,"children":2017},{"className":2016},[],[2018],{"type":386,"value":2019},"Volumes/Time Machine/myster-theater/nrl-no-ads",{"type":377,"tag":382,"props":2021,"children":2022},{},[2023,2025,2032,2034,2039,2041,2051,2053,2063,2065],{"type":386,"value":2024},"Upload to ",{"type":377,"tag":434,"props":2026,"children":2029},{"href":2027,"rel":2028},"https://archive.org/details/cbsrmt-nrl-ad-free-collection",[438],[2030],{"type":386,"value":2031},"your collection in archive.org",{"type":386,"value":2033}," by going to ",{"type":377,"tag":434,"props":2035,"children":2037},{"href":2027,"rel":2036},[438],[2038],{"type":386,"value":2027},{"type":386,"value":2040},", clicking ",{"type":377,"tag":434,"props":2042,"children":2045},{"href":2043,"rel":2044},"https://archive.org/edit/cbsrmt-nrl-ad-free-collection",[438],[2046],{"type":377,"tag":1865,"props":2047,"children":2048},{},[2049],{"type":386,"value":2050},"edit",{"type":386,"value":2052}," then clicking ",{"type":377,"tag":434,"props":2054,"children":2057},{"href":2055,"rel":2056},"https://archive.org/edit.php?edit-files=1&identifier=cbsrmt-nrl-ad-free-collection",[438],[2058],{"type":377,"tag":1865,"props":2059,"children":2060},{},[2061],{"type":386,"value":2062},"I want to change the files",{"type":386,"value":2064}," - or ",{"type":377,"tag":434,"props":2066,"children":2069},{"href":2067,"rel":2068},"https://archive.org/upload/?identifier=cbsrmt-nrl-ad-free-collection",[438],[2070],{"type":386,"value":2071},"try clicking this",{"type":377,"tag":382,"props":2073,"children":2074},{},[2075,2077],{"type":386,"value":2076},"The \"CBS Radio Mystery Theater\" spreadsheet is the \"source of truth\" and should be updated:",{"type":377,"tag":671,"props":2078,"children":2079},{},[2080,2182,2240,2264],{"type":377,"tag":382,"props":2081,"children":2082},{},[2083,2085,2091,2093],{"type":386,"value":2084},"Specify that this file has a no-ads variant by opening the \"CBS Radio Mystery Theater\" spreadsheet, navigating to the ",{"type":377,"tag":2086,"props":2087,"children":2088},"del",{},[2089],{"type":386,"value":2090},"\"Ken Long URLs\"",{"type":386,"value":2092}," \"NRL Ad Free\" sheet, and:\n",{"type":377,"tag":671,"props":2094,"children":2095},{},[2096,2106,2116,2170],{"type":377,"tag":382,"props":2097,"children":2098},{},[2099,2101],{"type":386,"value":2100},"Putting the episode number in the first column, ",{"type":377,"tag":1865,"props":2102,"children":2103},{},[2104],{"type":386,"value":2105},"Episode ID",{"type":377,"tag":382,"props":2107,"children":2108},{},[2109,2111],{"type":386,"value":2110},"Putting the original URL to the version with ads in the second column, ",{"type":377,"tag":1865,"props":2112,"children":2113},{},[2114],{"type":386,"value":2115},"Original URL",{"type":377,"tag":382,"props":2117,"children":2118},{},[2119,2121,2134,2136,2141,2143,2149,2151],{"type":386,"value":2120},"pasting in the file name ",{"type":377,"tag":1720,"props":2122,"children":2123},{},[2124,2126,2132],{"type":386,"value":2125},"without the ",{"type":377,"tag":592,"props":2127,"children":2129},{"className":2128},[],[2130],{"type":386,"value":2131},".mp3",{"type":386,"value":2133}," extension",{"type":386,"value":2135}," to in the third column, ",{"type":377,"tag":1865,"props":2137,"children":2138},{},[2139],{"type":386,"value":2140},"NRL Filename",{"type":386,"value":2142},". For the above, that would be the string ",{"type":377,"tag":592,"props":2144,"children":2146},{"className":2145},[],[2147],{"type":386,"value":2148},"0057 740608 The Fall Of The House Of Usher WOR (no ads)",{"type":386,"value":2150},". ",{"type":377,"tag":2086,"props":2152,"children":2153},{},[2154,2156,2161,2163,2168],{"type":386,"value":2155},"In the same row, add a ",{"type":377,"tag":1720,"props":2157,"children":2158},{},[2159],{"type":386,"value":2160},"1",{"type":386,"value":2162}," under the \"preferred for episode\" column (or a ",{"type":377,"tag":1720,"props":2164,"children":2165},{},[2166],{"type":386,"value":2167},"2",{"type":386,"value":2169}," if there are other usable recordings)",{"type":377,"tag":382,"props":2171,"children":2172},{},[2173,2175,2180],{"type":386,"value":2174},"Paste the contents of the exported label files in the fourth column ",{"type":377,"tag":1865,"props":2176,"children":2177},{},[2178],{"type":386,"value":2179},"Sections Excluded",{"type":386,"value":2181},". This is in case at some point in the future an episode needs to be edited or a better method for splicing episodes becomes available.",{"type":377,"tag":382,"props":2183,"children":2184},{},[2185,2187],{"type":386,"value":2186},"Add a description and tags to the episode in the \"NRL Descriptions\" sheet. Current tags are:\n",{"type":377,"tag":671,"props":2188,"children":2189},{},[2190,2195,2200,2205,2210,2215,2220,2225,2230,2235],{"type":377,"tag":382,"props":2191,"children":2192},{},[2193],{"type":386,"value":2194},"\"sci-fi\"",{"type":377,"tag":382,"props":2196,"children":2197},{},[2198],{"type":386,"value":2199},"\"whodunnit\"",{"type":377,"tag":382,"props":2201,"children":2202},{},[2203],{"type":386,"value":2204},"\"thriller\"",{"type":377,"tag":382,"props":2206,"children":2207},{},[2208],{"type":386,"value":2209},"\"paranormal\"",{"type":377,"tag":382,"props":2211,"children":2212},{},[2213],{"type":386,"value":2214},"\"crime\"",{"type":377,"tag":382,"props":2216,"children":2217},{},[2218],{"type":386,"value":2219},"\"drama\"",{"type":377,"tag":382,"props":2221,"children":2222},{},[2223],{"type":386,"value":2224},"\"mystery\"",{"type":377,"tag":382,"props":2226,"children":2227},{},[2228],{"type":386,"value":2229},"\"supernatural\"",{"type":377,"tag":382,"props":2231,"children":2232},{},[2233],{"type":386,"value":2234},"\"murder\"",{"type":377,"tag":382,"props":2236,"children":2237},{},[2238],{"type":386,"value":2239},"\"psychological\"",{"type":377,"tag":382,"props":2241,"children":2242},{},[2243,2245,2249,2251,2256,2258,2263],{"type":386,"value":2244},"If the audio of the episode is of acceptable quality, put a ",{"type":377,"tag":1720,"props":2246,"children":2247},{},[2248],{"type":386,"value":2160},{"type":386,"value":2250}," for \"best audio quality.\" If it's listenable but has a significant issue (part of it is missing or hard to hear) give it a ",{"type":377,"tag":1720,"props":2252,"children":2253},{},[2254],{"type":386,"value":2255},"-1",{"type":386,"value":2257},". If its quality is too low to be enjoyable, give it a ",{"type":377,"tag":1720,"props":2259,"children":2260},{},[2261],{"type":386,"value":2262},"-2",{"type":386,"value":1985},{"type":377,"tag":382,"props":2265,"children":2266},{},[2267,2269,2273,2275],{"type":386,"value":2268},"If the episode (plot, acting, writing, etc.) is especially enjoyable, give it a ",{"type":377,"tag":1720,"props":2270,"children":2271},{},[2272],{"type":386,"value":2160},{"type":386,"value":2274}," under ",{"type":377,"tag":1865,"props":2276,"children":2277},{},[2278],{"type":386,"value":2279},"Recommended",{"type":377,"tag":382,"props":2281,"children":2282},{},[2283,2285],{"type":386,"value":2284},"Export the spreadsheet as a CSV to ",{"type":377,"tag":592,"props":2286,"children":2288},{"className":2287},[],[2289],{"type":386,"value":2290},"~/Projects/web/mystery-theater-browser-content-support",{"type":377,"tag":382,"props":2292,"children":2293},{},[2294,2296,2302],{"type":386,"value":2295},"Run the \"Mystery Theater Scraper\" project (located in ",{"type":377,"tag":592,"props":2297,"children":2299},{"className":2298},[],[2300],{"type":386,"value":2301},"~/Projects/Experiments 2021/Mystery Radio Scraper",{"type":386,"value":2303},"). It will parse the CSV files at the path exported to above and output the content files that the site can read.",{"type":377,"tag":422,"props":2305,"children":2306},{},[2307,2309,2314],{"type":386,"value":2308},"If you want to add an episode but don't need to create an ad-free version, you can follow the steps above starting with step 10, but don't put anything in the ",{"type":377,"tag":1720,"props":2310,"children":2311},{},[2312],{"type":386,"value":2313},"ad-free variant",{"type":386,"value":2315}," column.",{"type":377,"tag":422,"props":2317,"children":2318},{},[2319],{"type":386,"value":2320},"What would be better:",{"type":377,"tag":422,"props":2322,"children":2323},{},[2324],{"type":386,"value":2325},"A tool that could:",{"type":377,"tag":378,"props":2327,"children":2328},{},[2329,2334,2339,2344],{"type":377,"tag":382,"props":2330,"children":2331},{},[2332],{"type":386,"value":2333},"Preview all the available MP3s",{"type":377,"tag":382,"props":2335,"children":2336},{},[2337],{"type":386,"value":2338},"Edit the CSVs directly",{"type":377,"tag":382,"props":2340,"children":2341},{},[2342],{"type":386,"value":2343},"Allow you to open an MP3 and select segments to remove & export new MP3",{"type":377,"tag":382,"props":2345,"children":2346},{},[2347],{"type":386,"value":2348},"Run the scraper process",{"type":377,"tag":654,"props":2350,"children":2352},{"id":2351},"issue",[2353],{"type":386,"value":2354},"Issue",{"type":377,"tag":422,"props":2356,"children":2357},{},[2358,2360,2366],{"type":386,"value":2359},"Discovered (from a review on archive.org) that two episodes from the BoA collection didn't download properly and weren't titled properly. Both contained ",{"type":377,"tag":592,"props":2361,"children":2363},{"className":2362},[],[2364],{"type":386,"value":2365},"$",{"type":386,"value":2367},". Assuming some issue with a Bash script (is that what I used?).",{"type":377,"tag":422,"props":2369,"children":2370},{},[2371],{"type":386,"value":2372},"Incorrect filenames:",{"type":377,"tag":378,"props":2374,"children":2375},{},[2376,2381],{"type":377,"tag":382,"props":2377,"children":2378},{},[2379],{"type":386,"value":2380},"/CBSRMT-791114-1030-The-,000-Error-(128-44)_no-id-{BoA} 2.mp3",{"type":377,"tag":382,"props":2382,"children":2383},{},[2384],{"type":386,"value":2385},"/CBSRMT-810415-1185-The-Fatal-,000-(128-44)_KQV-{BoA} 2.mp3",{"type":377,"tag":422,"props":2387,"children":2388},{},[2389],{"type":386,"value":2390},"Correct filenames:",{"type":377,"tag":378,"props":2392,"children":2393},{},[2394,2399],{"type":377,"tag":382,"props":2395,"children":2396},{},[2397],{"type":386,"value":2398},"/CBSRMT 791114 1030 The $999,000 Error (128-44)_no id {BoA}.mp3",{"type":377,"tag":382,"props":2400,"children":2401},{},[2402],{"type":386,"value":2403},"/CBSRMT 810415 1185 The Fatal $50,000 (128-44)_KQV {BoA}.m3",{"type":377,"tag":654,"props":2405,"children":2407},{"id":2406},"transcribing",[2408],{"type":386,"value":2409},"Transcribing",{"type":377,"tag":422,"props":2411,"children":2412},{},[2413,2415,2421],{"type":386,"value":2414},"You installed ",{"type":377,"tag":434,"props":2416,"children":2419},{"href":2417,"rel":2418},"https://github.com/openai/whisper",[438],[2420],{"type":386,"value":351},{"type":386,"value":2422},". General usage:",{"type":377,"tag":587,"props":2424,"children":2426},{"code":2425},"~/Projects/other-experiments/whisper $ whisper --model [tiny or small].en --language en [path.mp3]\n",[2427],{"type":377,"tag":592,"props":2428,"children":2429},{"__ignoreMap":369},[2430],{"type":386,"value":2425},{"type":377,"tag":422,"props":2432,"children":2433},{},[2434,2436,2442,2444,2450,2452,2458,2460,2466,2468,2474,2476,2482],{"type":386,"value":2435},"Creates text files at ",{"type":377,"tag":592,"props":2437,"children":2439},{"className":2438},[],[2440],{"type":386,"value":2441},"[path.mp3.txt]",{"type":386,"value":2443}," and ",{"type":377,"tag":592,"props":2445,"children":2447},{"className":2446},[],[2448],{"type":386,"value":2449},"[path.mps.vtt]",{"type":386,"value":2451},", where the ",{"type":377,"tag":592,"props":2453,"children":2455},{"className":2454},[],[2456],{"type":386,"value":2457},".txt",{"type":386,"value":2459}," is just the text, and the ",{"type":377,"tag":592,"props":2461,"children":2463},{"className":2462},[],[2464],{"type":386,"value":2465},".vtt",{"type":386,"value":2467}," is a human-readable captioning format with time stamps. The ",{"type":377,"tag":592,"props":2469,"children":2471},{"className":2470},[],[2472],{"type":386,"value":2473},"small",{"type":386,"value":2475}," model is good, the ",{"type":377,"tag":592,"props":2477,"children":2479},{"className":2478},[],[2480],{"type":386,"value":2481},"tiny",{"type":386,"value":2483}," model is fast.",{"type":377,"tag":422,"props":2485,"children":2486},{},[2487],{"type":386,"value":2488},"Of interest for two reasons:",{"type":377,"tag":378,"props":2490,"children":2491},{},[2492,2504],{"type":377,"tag":382,"props":2493,"children":2494},{},[2495,2497,2502],{"type":386,"value":2496},"Could be used to transcribe entire episodes fairly accurately for searching and presentation on site. But the ",{"type":377,"tag":592,"props":2498,"children":2500},{"className":2499},[],[2501],{"type":386,"value":2473},{"type":386,"value":2503}," model is about 1:1 for time-to-transcribe, that is, it takes an hour to transcribe an hour of audio.",{"type":377,"tag":382,"props":2505,"children":2506},{},[2507,2509,2514],{"type":386,"value":2508},"Could be used to more quickly find ads. The ",{"type":377,"tag":592,"props":2510,"children":2512},{"className":2511},[],[2513],{"type":386,"value":2481},{"type":386,"value":2515}," model seems to take about 10 minutes for an episode. Then you can search for \"be back\" or \"for act\" to try to find commercial breaks and see their time stamps. This actually works well - much more pleasant and faster to scan text than to scrub audio.",{"type":377,"tag":422,"props":2517,"children":2518},{},[2519],{"type":386,"value":2520},"There's a python library. So close to, but not quite able to, just having it transcribe an episode, finding the ad breaks, and trimming them automatically. For example, time stamps don't take into account music; lines don't care about different voices (I'll be back for Act II shortly. Your local Buick dealer is offering…).",{"title":369,"searchDepth":736,"depth":736,"links":2522},[2523],{"id":1775,"depth":736,"text":1778,"children":2524},[2525,2526,2527],{"id":1817,"depth":739,"text":1820},{"id":2351,"depth":739,"text":2354},{"id":2406,"depth":739,"text":2409},"content:notes-to-self:mystery-theater.md","notes-to-self/mystery-theater.md","notes-to-self/mystery-theater",1776608499014]