20 years ago you had to be fluent in the deep arcana of low-level details to be a good programmer. You also could not lean on deep, rich libraries to get the job done because such libraries were far and few between. There was nothing good about this per se, it was a fact of reality. It also made it difficult and slow to get work done.
Today, development environments are rich in both tools and libraries beyond the wildest dreams of programmers two decades ago. You can implement incredibly complex applications without touching any of the low-level supporting code and expect reasonable results. That is the banner of progress.
However, this characterization of current software development is only true at the median. At the high-end, you still require a deep understanding of low-level systems, have to build your own libraries, and be able to wrangle esoteric computer science to be a good programmer. Many years ago, there were a great many programmers with these skills because you needed them to get the most rudimentary jobs done. Today, I see many more software engineers that completely lack these skills because they never needed to learn them to become a good, marketable programmer.
That is an important distinction. It is not to say that earlier generations of programmers had more intrinsic ability, but they did have skills that are relevant today to designing software on the very high-end that are much less frequently learned now. To a significant extent it was a product of environment. Ironically, many of the primitive skills that were relevant many years ago have become cornerstones of writing high-performance and scalable software systems today.