cmiles - info

Life, Tech and Unimportant Minutiae

Created by Charles on 8/1/2025. Updated on 12/31/2025.

The Pointless Waymarks GeoTools and Pointless Waymarks CMS have both had the ability to take position information and compare it to GeoJSON reference data to automatically create tags for content, such as photographs, for some time now.

For example, the photo below is tagged with:

arizona,coral bean,coronado national forest,pima county,rincon mountain wilderness,rincon mountains,santa catalina ranger

Of those tags the following were created automatically:

arizona,coronado national forest,pima county,rincon mountain wilderness,rincon mountains,santa catalina ranger district

2024 December Coral Beans
2024 December Coral Beans. Charles Miles. 12/9/2024.

For me, it has been great to have automatic, accurate tagging of land ownership/management, trails and various other geographic minutiae that I care about.

I was on Wheeler Peak in Great Basin National Park earlier this year and took a few photos at sunset. At home, I used the Pointless Waymarks GeoTools to add locations to my photos and then generate tags. The generated tags were helpful, but I was slightly disappointed that my photos from the summit weren't automatically tagged 'wheeler peak' - this led to two improvements.

Buffering Locations

Wheeler Peak and my photo are both represented by a single point. This representation is both completely true and somewhat unhelpful. On the one hand the 'true summit' of Wheeler Peak is a single point - but it doesn't make sense to only tag photos standing exactly on that point 'Wheeler Peak' and almost no one works with equipment that is accurate enough to even reliably identify when you are on the exact point!

2025 August Geo Tools Buffer Setting
2025 August Geo Tools Buffer Setting.

To better match points and lines code has been updated to accept a setting that allows buffering source point and line data. The point for the Wheeler Peak photograph now becomes a circle that covers, and allows matching to, Wheeler Peak.

OSM/Overpass

My experience is that if you are interested in tagging landscape photos no single data source will have everything you are interested in, and some details (local names are a good example) might not be present in any data source. With that in mind, the first version of the Feature Intersect Tags used local GeoJson files (generally an easy format to export geographic data into) and local PAD-US Data data. Two important benefits of this approach:

  • No dependence on online services being up and available
  • Ability to create custom files that combine, exclude and edit data sources into exactly what you want (QGIS may be useful here)`
  • GeoJSON is supported by a variety of tools (geojson.io for example) and with some care can be edited in a text editor

The downside is that you have to collect and curate all the data yourself. This is too much setup for an average user. Even for me this setup worked best for my local area where the time and effort to create curated reference files has a great return on investment.

While there is no perfect source of truth for trails, peaks, rivers and other landscape features OpenStreetMap has an impressive amount of relevant data that is available thru the Overpass API.

Overpass turbo and QGIS+the QuickOSM Plugin are two ways to explore this data and to experiment with the API.

2025 August Geo Tools OSM Overpass Tagging Settings
2025 August Geo Tools OSM Overpass Tagging Settings.

The Pointless Waymarks GeoTools and Pointless Waymarks CMS can now use the settings above to tag the my Wheeler Peak photo with:

great basin national park,nevada,united states,wheeler peak,wheeler peak summit trail,white pine county

2025 July Sunset from Wheeler Peak
2025 July Sunset from Wheeler Peak. Charles Miles. 6/15/2025.
2025 August Geo Tools Results for a Wheeler Peak Photo including OSM Results
2025 August Geo Tools Results for a Wheeler Peak Photo including OSM Results.

Nothings Perfect...

Overall the inclusion of buffering and OSM data has been a nice step forward for tagging in the Pointless Waymarks software - but it isn't without some challenges...

Noise

Buffering is crucial for including all the features you want to generate tags from, but it will inevitably include some that are less valuable. A good example is buffering the track/line from a trail run and generating tags - buffering+OSM data makes it very likely that the names of the trails you ran are returned as tags - great! But it also makes it likely that the names of intersecting trails you ran past are returned as tags... In some cases that is great - it may be useful to look back and see that you ran past a junction, and nice that all adjoining activities come up in a tag search for the run. But here is a more obviously not-useful example - a 55-mile bike ride from 2011 tagged with OSM and my usual settings and files produced these tags:

1st avenue,3rd st bicycle boulevard,ace hardware,alamo wash,albertsons,alvernon optical,alvord road,arcadia wash,arizona,arizona trail,avenida de la potranca,bbva,box canyon,box canyon wash,brandi fenton memorial park,broadway jessica,broadway kolb,broadway langley,broadway northeast,broadway smiles denistry,broadway wilmot,bus 15,bus 17,bus 3,bus 37,bus 7,cactus forest drive,cactus forest trail,calle cipres,calle santo,camino de garanon,camino real,campbell ave,campbell plaza,casa loma condominiums,casa loma estates,casas lindas,centrepark drive,cienega creek pantano wash,cloud ridge,columbus boulevard,conner park,contempo drive,copper star condominiums,craycroft,discovery ridge open space,duffy family community center,eardlina avenue,east 1st street,east 22nd street,east 29th street,east 2nd street,east 3rd street,east 4th street,east 5th street,east 6th street,east 8th street,east 9th street,east acoma place,east adams street,east alandale place,east alberta drive,east arrowhead drive,east avenida del cazador,east baker street,east bellevue street,east blacklidge drive,east broadway boulevard,east bromley street,east buddy lane,east burns street,east calle arizona,east calle de amigos,east calle javelina,east calle ojos verde,east calle villa rica,east camino bacelar,east camino del desierto,east camino del rio,east chauncey street,east citrus avenue,east cloud road,east colette street,east country club vista drive,east croydon park road,east delano street,east desert oak trail,east drexel road,east elida street,east escalante road,east fairmount street,east farness drive,east florence drive,east fort lowell road,east freeman place,east glenn street,east golf links road,east grant road,east graybill drive,east halcyon road,east harborage drive,east hawthorne street,east helen street,east holaway drive,east irvington road,east jeremy crossing road,east joan place,east kenyon drive,east knox drive,east la madera drive,east laguna street,east lazy r ranch road,east lazy ranch road,east lee street,east lester street,east limberlost drive,east linden court,east linden place,east mc millan drive,east mohave road,east monte vista drive,east navajo road,east old spanish terrace,east old spanish trail,east oldooz place,east pantano trail,east pastime road,east peach street,east pima street,east portal airosa,east prince road,east river front drive,east river oak trail,east river road,east roger road,east rosewood street,east saguaro crest place,east seneca street,east shoreline drive,east smoot drive,east south regency circle,east spanish ridge place,east speedway boulevard,east tanque verde lane,east tanque verde road,east thunderhead ranch road,east vactor ranch trail,east waverly street,east wetmore road,east willard street,east wind dancer drive,east wrightstown road,east yavapai road,el dorado,el gheko,entrada,evening mist lane,flap,george mehl family foothills district park,glenn campbell ne,glenn east,handmaker assisted living facilities,hidden glenn,kimberly woods apartments,kingston knolls terrace,la madera,la madera park,lamadera park,liberty tax,life spa,manana vista,mehl foothills park,mesquite grove,miramonte,mountain 1st avenue,mountain avenue,mountain view avenue,nailz,norte corte melodia,north 1st avenue,north alvernon way,north arcadia avenue,north avenida de la vista,north avenida de san ramon,north avenida del cazador,north avenida la vallita,north avenida natachee,north avenida valiente,north bacobi avenue,north beverly avenue,north calle agua verde,north calle de amigos,north calle rosario,north camino arco,north camino blanco,north camino cardenal,north camino castile,north camino de la puerta,north camino de lupo,north camino del celador,north camino del obispo,north camino escuela,north camino gacela,north camino kino,north camino luz,north camino pio decimo,north camino real,north camino rio soleado,north camino seco,north camino sinuoso,north camino sumo,north campana drive,north campbell avenue,north campbell estates,north cherry avenue,north columbus boulevard,north country club road,north craycroft road,north desert avenue,north dodge boulevard,north east plaza drive,north eastgate drive,north edith boulevard,north euclid avenue,north fair oaks avenue,north flagstaff place,north flanwill boulevard,north forgeus avenue,north four winds drive,north hacienda del sol road,north hampton street,north highland avenue,north indian ruins road,north jessica avenue,north kolb road,north langley avenue,north laurel avenue,north leonora avenue,north longfellow avenue,north maguire avenue,north martin avenue,north montego drive,north mountain avenue,north mountain view avenue,north old sabino canyon road,north olsen avenue,north orlando avenue,north palo verde boulevard,north pantano road,north park avenue,north placita vida,north plumer avenue,north pontatoc road,north prudence road,north ralph avenue,north richey boulevard,north rio cancion,north rio verde vista drive,north river gate place,north river hills drive,north river ranch place,north rosemont boulevard,north round rock drive,north sabino canyon road,north san sebastian drive,north santa rosa avenue,north sarnoff drive,north silkie place,north sparkman boulevard,north sutton lane,north swan road,north sycamore avenue,north tanuri drive,north torino avenue,north treat avenue,north tucson boulevard,north tyndall avenue,north venice avenue,north via encantadora,north via entrada,north walnut avenue,north warren avenue,north west plaza drive,north wilmot road,north wilson avenue,north winslow drive,north winstel boulevard,north wyatt drive,old spanish trail,old spanish trail greenway,palo verde park,pantano river park,pantano wash,park avenue,paseo rancho esperanza,pima county,pima street baptist church,placita casa ri,proposed gateway center,reflection vista,rillito river,rillito river park,rillito river path,rincon creek,rincon mountains,rincon valley,rio vista,river rd,river road circle,rob wash,rose hill wash,route 3 6th st wilmot eastbound,route 3 6th st wilmot westbound,sabino canyon,sabino vista circle,saguaro national park,san rafael estates,sandpiper apartments,sauce pizza wine,shaheen estates,south avenida los reyes,south blacksburg avenue,south brown avenue,south calle mesa del oso,south camino seco,south dakota sky court,south desert vista drive,south discovery lane,south ferris drive,south floral ridge way,south freeman road,south gollob road,south harrison road,south houghton road,south mann avenue,south melpomene way,south monument view way,south old spanish trail,south pantano road,south pedregal drive,south placita carrasco,south prudence road,south rainwater lane,south reflection vista place,south rocking k ranch loop,south sarnoff drive,south sherwood village drive,south speckled stone way,south star vista drive,south van buren avenue,south woodstock drive,st phillips plaza,sun tran route 1 glenn swan eastbound,sun tran route 1 glenn swan westbound,sun tran route 103x northwest-downtown express,sun tran route 105x foothills-downtown express,sun tran route 108x broadway-downtown express,sun tran route 109x catalina highway-downtown express,sun tran route 11 alvernon,sun tran route 15 campbell northbound from tucson marketplace,sun tran route 15 campbell southbound to banner umc south campus,sun tran route 17 county club golf links to tohono tadai transit center,sun tran route 17county club golf links to broadway houghton park and ride,sun tran route 201x eastside-aero park express,sun tran route 34 craycroft fort lowell northbound,sun tran route 34 craycroft fort lowell southbound,sun tran route 37 pantano northbound,sun tran route 37 pantano southbound,sun tran route 4 speedway eastbound to golf links at kolb,sun tran route 4 speedway eastbound to houghton at broadway,sun tran route 4 speedway westbound from golf links at kolb,sun tran route 4 speedway westbound from houghton at broadway,sun tran route 5 pima west speedway east bound,sun tran route 5 pima west speedway westbound,sun tran route 6 euclid north 1st avenue northbound,sun tran route 6 euclid north 1st avenue southbound,sun tran route 7 22nd street eastbound,sun tran route 7 22nd street westbound,sun tran route 8 broadway eastbound to houghton at broadway,sun tran route 8 broadway eastbound to udall station,sun tran route 8 broadway westbound from houghton at broadway,sun tran route 8 broadway westbound from udall station,sun tran route 9 grant eastbound,sun tran route 9 grant westbound,sun tran route 9 westbound,tanque verde wash,the loop,thunderhead ranch,treat,ventana cayon wash

I didn't hand check all the results but I suspect that these are all true/accurate - but I'm doubting that anyone, regardless of their approach to tagging, would find this useful. I suppose that the code could try to determine 'most relevant' tags in this circumstance - or maybe the tag set and linestring could be passed to an AI with a prompt for the most useful tags - for now, I've simply added an option in the CMS to tag Line Content without using OSM.

API Limits - API Strategy

In anything other than testing and experimenting it is easy to hit the API limits. It isn't complicated to deal with this - it would have been easier if I had realized it was going to happen from the beginning...

'In' Tagging

Disclaimer: I'm not an expert with the Overpass API so there may be approaches and features I am not aware of!

The best way I found to get the areas that a point is in - National Parks, State, Country, Wilderness Areas - is via an 'in' query to Overpass. This (with some filtering for areas like time zones that you are unlikely to want in your tags) works well for a single point, but there isn't a variation of 'in' where you pass in a linestring or polygon. This creates a puzzle regarding getting good information from Overpass about the various land ownership and management areas that a run or hike passes thru especially since both API Limits and good manners dictate that it isn't reasonable to submit every point from a long GPS track to the API for a query. For now, I'm using a simple algorithm the GitHub Copilot helped me write to get a very limited set of points for a line - probably a good enough solution even though it won't catch everything.


Created and Updated by Charles on 3/30/2025.

After a number of months of continuous operation the Pi Zero 2 Wh running my Vibration Monitor Software dropped offline.

I expected it to come back after power cycling it - it didn't. I then suspected that the MicroSD card had an issue - it wasn't. Flaky power supply? No. Pi killed by the heat? The Tucson summer can be very warm, but not the problem. Bad luck? Not really...

2025 March Corrosion and Rust on an SW-420 Vibration Sensor and Wiring
2025 March Corrosion and Rust on an SW-420 Vibration Sensor and Wiring. Charles Miles. 3/30/2025.

One of the things I love about occasionally trying small Raspberry Pi Projects is that I'm always learning new things! In this case, lacking hardware/sensor experience, I hadn't considered the impact of moisture on the wiring and the vibration sensor. Everything you see from the sensor is quite dry, but even in the desert the buried plastic box this sensor was in has condensation and moisture.

In the short term I just replaced hardware - but now on the todo list is protecting the sensors and doing different wiring that will hopefully let this system live a longer life...

PS - I replaced the Pi Zero 2 Wh with a Pi 3 A+ - I was absolutely blown away by the size of the Pi Zero 2 Wh when I got it - it is certainly the smallest hardware I have ever run C#/.NET code on!! But over time I found the 2.4GHz only Wifi and lack of a full-sized HDMI port (ie easy connection to the monitors I own) were too much of a downside - for me the Pi 3 A+ remains a sweet spot in the Pi line.


Created by Charles on 3/11/2025. Updated on 3/19/2025.

Recently I moved my personal projects to Fossil. The move has been fun and interesting!

I'm newer to Fossil and so far for my reasonably simple use cases the cli + built in website have been an easy to work with combination.

But I miss Fork - a fast and friendly git client for Mac and Windows...

What I miss:

  • Quick view of changed and added files powered by a file watcher so the view is mostly-almost-always up to date
  • Quick view of file diffs
  • Fast mouse-driven selection of files to take actions on - I often want to group a few files into a commit and I find clicking a GUI list of files is faster and easier than using the terminal
  • Dedicated Window - when something is important, like version control, it can be nice to have a dedicated window/app

So with a distinct lack of Fossil tooling out in the world I thought it would be fun to write my own helper program! Goals:

  • Fossil has a nice command line interface - try to work with it rather than hide it
  • Be careful about duplicating views and features already in Fossil's web interface
  • Target frequent operations - I suspect that there is no real time savings over the cli for commands that you run infrequently

After about 4 weeks of personal time effort this is what Pointless Fossil - a Fossil SCM Windows Gui Helper looks like:

2025 March Pointless Fossil Main Window
2025 March Pointless Fossil Main Window.

It is very new but I'm actively using and enjoying it. This is very much a work in progress - not enough time to develop any interesting insights - but a few details that might be of interest are below.

Avalonia UI

Avalonia UI is one of several interesting cross-platform options for building desktop applications with .NET. Pointless Fossil is already the largest program I have ever built with Avalonia and overall it has been a positive experience. It seems to me that vs WPF you gain cross-platform potential and occasional syntax/framework improvements - you lose the large body of online help, there are fewer packages/less code available and there is not a great embedded web view.

Fossil JSON API

Fossil has a JSON API that allows you to retrieve information about the state of a repository - VERY useful!! But in the official binaries the json api is not available... To access the JSON API you will have to compile a custom version of Fossil - there is good documentation available, but this was an unexpected todo on the way to getting a working program!

Reading Standard Output

A requirement for the program was allowing the user to respond if Fossil asked a question on the command line. I hadn't written a similar feature before and I assumed that writing to stdin was going to be the messy part. It turned out that stdin wasn't the problem - many of the questions Fossil asks don't end with a new line and I was surprised by the code needed to read stdout in characters rather than lines! GitHub Copilot was very helpful in working out the details - the start of my code is below, I still can't help but wonder if there is a better/simpler way...

        var buffer = new byte[1024];
        var charBuffer = new char[1024];
        var decoder = Encoding.UTF8.GetDecoder();
        int bytesRead;

        while ((bytesRead = await reader.BaseStream.ReadAsync(buffer, 0, buffer.Length)) > 0)
        {
            var charsDecoded = decoder.GetChars(buffer, 0, bytesRead, charBuffer, 0);
            for (var i = 0; i < charsDecoded; i++)

DiffPlex

DiffPlex is Netstandard 1.0+ C# library to generate textual diffs - in addition to the core functionality WinUI, WPF, WinForms and Avalonia (via BAndysc's DiffPlex.Avalonia) controls are available. This MIT licensed library is definitely worth being aware of!


Created by Charles on 1/12/2025. Updated on 3/11/2025.

2025 January GitHub Screenshot
GitHub's front page on 1/12/2025.

Git+GitHub is currently an amazing combination. Git has incredible functionality, tooling and resources - GitHub hosts a huge number of projects, supports everything from individuals to enterprises, stars are currently one of the more notable measures of project popularity and GitHub sponsors can help support developers and projects.

For work, popularity and large collaborative open source projects Git+GitHub are an easy choice - for my personal projects I think it is time to make a change.

Here is what I have noticed about my use for personal projects over the past 5 or so years:

  • 99.9% of my work is as a single developer
  • For personal projects my git use tends to be simple - mostly development on main with an occasional branch
  • I browse code and changes on GitHub and appreciate the ReadMe.md functionality - but haven't made meaningful use of anything else
  • I am not looking for popularity/fame/stars...

And here is why I'm moving to Fossil+Chisel:

  • My current long-shot bet is that my interest in my personal code and projects outlives the current (largely friendly+happy+zero-cost-for-simple-use) incarnation of GitHub.
  • I am not fully convinced that it will be possible, practical or desirable for me to host code online in 10/20/30 years - I'm currently moving to Chisel so that my code is hosted offsite, but long-term Fossil's strong, built-in, website/forge functionality is very, very, attractive.
  • As much as possible I want to support what I love, believe in and care about, even if it is in small ways. Fossil is an interesting, long running, practical and functional developer tool that I want to support. A glance at the GitHub and Fossil homepages may give you a hint about my feelings - I want to be the Fossil homepage, not the GitHub homepage...
  • Fun and learning!

The hedge with all this is that it is easy enough to mirror from Fossil to GitHub these days - so for now I am creating mirrors on GitHub...

2025 January Fossil Screenshot
The front page of the Fossil project on 1/12/2025.

If you end up trying Chisel I think one common workflow is to import an existing Git repo - I'm not the person you want to ask about the best way to do this but basically I would point you to:

  • Fossil: Import And Export: Basics on importing and exporting.
  • How to push Fossil local repository to remote hosting - Stack Overflow: The answer with 10 steps is a good description of the workflow I used - BUT at least in Q1 2025 it looks like the key to getting this work is in the Flint bug report below.
  • Override project code - NOT working: Flint/Chisel currently has a bug where the 'Create Repository' screen gives you a critical and very helpful data entry field titled 'Override project code (Optional, but may be needed if pushing an already created repo to Chisel.)' - but it doesn't work. The workaround in the link is pretty simple, but maybe not when you are trying to figure out 'everything'.

Related Links and Notes:

My current public repos on Chisel:


Created and Updated by Charles on 1/20/2025.

The Pointless Waymarks Cloud Backup and Pointless Waymarks PowerShell Runner have been running happily on my main computer for a bit without me thinking about them.

2025 January Pointless Waymarks Cloud Backup Main Window before LiveCharts2
2025 January Pointless Waymarks Cloud Backup Main Window before LiveCharts2.
2025 January Power Shell Runner Job List before LiveCharts2
2025 January Power Shell Runner Job List before LiveCharts2.

I was glad that the programs had been doing their job - but I was disappointed that I couldn't verify they had done their job more quickly. The data about runs needed a better presentation - enter LiveCharts2 (on GitHub): "Simple, flexible, interactive & powerful charts, maps and gauges for .Net, LiveCharts2 can now practically run everywhere Maui, Uno Platform, Blazor-wasm, WPF, WinForms, Xamarin, Avalonia, WinUI, UWP."

The LiveCharts2 site site has galleries, code and documentation that make it quick to add simple charts. The charts are fairly new, so I'm still testing/working, but I'm happy with the first round of results!

2025 January Pointless Waymarks Cloud Backup Job List with Active Upload
2025 January Pointless Waymarks Cloud Backup Job List with Active Upload.
2025 January Pointless Waymarks PowerShell Runner Job List
2025 January Pointless Waymarks PowerShell Runner Job List.

Created and Updated by Charles on 1/12/2025.

My happy feeling of being caught up on a personal project was recently crushed when I realized that dragging a file from my Android phone onto the Pointless Waymarks CMS resulted in ... nothing.

Files on my Windows computer and files from various network shares dropped without issues into the app - and the files from the Android phone worked fine in Windows Explorer between locations - but dragging Android to a WPF app didn't work.

I quickly turned to my buddy GitHub Copilot, who has given me some nice drag-and-drop answers in the past. My buddy produced some code that looked probable - and failed first try (hard to believe that this isn't a standard behavior most people experience these days). In a bit of behavior that might prove that GitHub Copilot is fundamentally human when asked about the exception from its code, the response was to blame the (probably corrupt) incoming data!

I thrashed around for a while looking for different ideas and eventually ended up on a human answer from the depths of Stack Overflow - c# - Dropped zip file causes e.Data.GetData("FileContents") to throw an exception - Stack Overflow (as per usual be sure to read the comments on the answer - the bottom comments will save you some time).

As with many things, it is a little hard to understand why the .NET drag-and-drop abstractions don't help more in this case and leaves you mucking around with FORMATETC and binary formats.

My code based on c# - Dropped zip file causes e.Data.GetData("FileContents") to throw an exception - Stack Overflow (note that I use the GongSolutions.WPF.DragDrop in my WPF projects) can currently be found in the PointlessWaymarksTools Project:


Posts Before:
2025 January Photo Content Page Details Block - Before Update
2024 December Pointless Waymarks Feed Reader Feed Editor with Auto Mark Options
2024 December Pi Sliced Day Photos Solstice to Solstice Sunsets Video Cover Image
2024 December CMS Photo Direction Display
2024 June Pointless Waymarks Cloud Backup - Main Window