6502.org Forum  Projects  Code  Documents  Tools  Forum
It is currently Sun Jul 07, 2024 6:36 am

All times are UTC




Post new topic Reply to topic  [ 21 posts ]  Go to page Previous  1, 2
Author Message
PostPosted: Sun May 01, 2022 9:36 am 
Offline

Joined: Sat Oct 09, 2021 11:21 am
Posts: 707
Location: Texas
Nice bird! Your resolution makes mine look like a toy :) I really like the 15 color palette, it really "pops" and that's super important. Minus one color seems totally worth it. Which diode did you use in particular? It just says "schottky diode" on the schematic, no other identification.

Great job Bill! Looks great!

Chad


Top
 Profile  
Reply with quote  
PostPosted: Sun May 01, 2022 1:36 pm 
Offline

Joined: Fri Dec 21, 2018 1:05 am
Posts: 1086
Location: Albuquerque NM USA
The Schotty diode I used is 1N5817, a general diode that's readily available on eBay.

It is hard to take picture that accurately represent the colors on the monitor. The picture posted yesterday was a good representation of what's on the monitor, but many of my earlier pictures were washed out and that may be the case with other's monitor images.
Bill


Top
 Profile  
Reply with quote  
PostPosted: Mon May 02, 2022 4:29 am 
Offline

Joined: Fri Dec 21, 2018 1:05 am
Posts: 1086
Location: Albuquerque NM USA
I used Photoshop to convert "finch.jpg", a 512x480 image to 16-color image and save it as 4-bit BMP file. Converted the .BMP file to .HEX file with BIN2HEX. Because the data file is larger than 6502 memory can hold (.BMP data file is 122K), I created a program that reads in .HEX file and saves it directly to graphic memory. Because I can write to the graphic memory anytime, I don't need to worry about buffering up the .HEX data stream and find the right time to transfer data. It all worked out except the color mapping is not right. I'll need to change the color mapping in CPLD.

CRC65 has CF mass storage so now is time to think about a filing system for collection of .BMP files so I can retrieve images from CF disk directly.
Bill


Attachments:
finch.jpg
finch.jpg [ 74.8 KiB | Viewed 325 times ]
DSC_69500501.jpg
DSC_69500501.jpg [ 1.29 MiB | Viewed 325 times ]
Top
 Profile  
Reply with quote  
PostPosted: Mon May 02, 2022 10:11 am 
Offline

Joined: Sat Oct 09, 2021 11:21 am
Posts: 707
Location: Texas
plasmo wrote:
I used Photoshop to convert "finch.jpg", a 512x480 image to 16-color image and save it as 4-bit BMP file. Converted the .BMP file to .HEX file with BIN2HEX. Because the data file is larger than 6502 memory can hold (.BMP data file is 122K), I created a program that reads in .HEX file and saves it directly to graphic memory. Because I can write to the graphic memory anytime, I don't need to worry about buffering up the .HEX data stream and find the right time to transfer data. It all worked out except the color mapping is not right. I'll need to change the color mapping in CPLD.

CRC65 has CF mass storage so now is time to think about a filing system for collection of .BMP files so I can retrieve images from CF disk directly.
Bill


Looks good Bill! I think it is a good thing that you can change the color mapping on the CPLD, very easy.

So, I've worked with .bmp files for a long time over the years. I don't think of them as 'binary' files, so much as RGB color values. But hey, if this BIN2HEX works for you, neat!

One last thing: Whenever I am working with .bmp files, for some reason it always reads out as BGR instead. So maybe that's why your colormap is off some? Just a guess.

Great job!

Chad


Top
 Profile  
Reply with quote  
PostPosted: Mon May 02, 2022 10:18 am 
Offline

Joined: Fri Jul 09, 2021 10:12 pm
Posts: 741
plasmo wrote:
Yes, I would like to see your Python example. I know there are online image converter as well. I can also tweak the CPLD design to be compatible with the image conversion output.
Bill

Here are some of my old Python scripts - I tuned them on a case by case basis for whatever I needed to do at the time.

First of all, for a palettized image I'm pretty sure this works fine:

Code:
from PIL import Image

im = Image.open("finch-indexed.png")
with open("finch-indexed.img", "wb") as f:
   f.write(im.tobytes())
   f.close()


I've created some custom palettes in GIMP such as the 4-bit RGBI palette, a 3-bit RGB palette, and a 2-bit-per-pixel one with black, white, light blue, and orange, and used them for various things. GIMP seems better at reducing colour depth than PIL.

You often need to manipulate the data before writing it, but that's fairly easy to do in Python. In my 640x480x3bpp system, I store four pixels per "byte" with the red data in a separate "plane", and the green and blue data packed together, and also store the data backwards so that the loops on the 6502 count down rather than up:

Code:
from PIL import Image

im = Image.open("finch-640x480x3bpp.png")

print(im.size)
print(im.getpalette())


reddata = []
greenbluedata = []

def pack(bit,*v):
   r = 0
   for x in v:
      r <<= 1
      if x & bit:
         r += 1
   return r

for y in range(im.height):
   for x in range(0, im.width, 4):
      v0 = im.getpixel((x,y))
      v1 = im.getpixel((x+1,y))
      v2 = im.getpixel((x+2,y))
      v3 = im.getpixel((x+3,y))

      r = pack(1, v0, v1, v2, v3)
      g = pack(2, v0, v1, v2, v3)
      b = pack(4, v0, v1, v2, v3)

      reddata.append(r)
      greenbluedata.append((g << 4) + b)

print(len(reddata), len(greenbluedata))

with open("imgfinch.dat", "wb") as fp:
   fp.write(bytes(reversed(greenbluedata)))
   fp.write(bytes(reversed(reddata)))
   fp.close()

This last file is quite large (about 300k I think) and it gets written to an SD card rather than being embedded in the code.

But I've also used PIL for this as follows - one advantage being that you can tweak the palette in code and see what the results are like, or preview what it would look like with different hardware configurations before committing to them:

Code:
from PIL import Image
from PIL import ImagePalette


# Create a palette that matches what the hardware does
palette = []
for v in range(16):
   base = 0
   mag = 160
   if v>=8:
      base += 255-mag

   r = base + mag * ((v>>2)&1)
   g = base + mag * ((v>>1)&1)
   b = base + mag * ((v>>0)&1)

   palette.extend((r,g,b))


# Make a copy of the palette with some bias towards 0x80, so that the quantization works better
palettedata = []
bias = 12
for v in range(16):
   r,g,b = palette[3*v:3*(v+1)]

   r = bias + (r * (0xff-2*bias)) // 0xff
   g = bias + (g * (0xff-2*bias)) // 0xff
   b = bias + (b * (0xff-2*bias)) // 0xff

   palettedata.extend((r,g,b))


# PIL requires 256-colour palettes
palettedata.extend([0] * (768-len(palettedata)))


# PIL has a quirky API that requires us to wrap an image around the palette in order to use it
palimage = Image.new("P", (1,1))
palimage.putpalette(palettedata)


im = Image.open("finch.jpg")

im2 = im.resize((160,100)).quantize("P", palette=palimage, kmeans=10)
im2.save("finch2.png")

# Save out a scaled-up version of the palettized image so that it's easier to see for debugging
scale = 8
im3 = Image.new("RGB", (im2.width*scale,im2.height*scale))
for y in range(im2.height):
   for x in range(im2.width):
      v = im2.getpixel((x,y)) & 15
   for v in range(16):
      r,g,b = palette[3*v:3*(v+1)]

      r = bias + (r * (0xff-2*bias)) // 0xff
      g = bias + (g * (0xff-2*bias)) // 0xff
      b = bias + (b * (0xff-2*bias)) // 0xff

      palettedata.extend((r,g,b))
      r,g,b = palette[3*v:3*(v+1)]
      for xx in range(scale):
         for yy in range(scale):
            im3.putpixel((x*scale+xx,y*scale+yy),(r,g,b))

im3.save("finch3.png")


# Save out the binary data
with open("finch.img", "wb") as f:
   f.write(im2.tobytes())
   f.close()

Ultimately it looks like I stopped using PIL for palettization though.


Top
 Profile  
Reply with quote  
PostPosted: Wed May 18, 2022 6:43 pm 
Offline
User avatar

Joined: Tue Aug 11, 2020 3:45 am
Posts: 311
Location: A magnetic field
plasmo on Tue 4 Jan 2022 wrote:
* Combined text-based VGA with graphic VGA


I thought that Hal W. Hardenbergh's infamous DTACK Grounded newsletter advocated this approach. However, it advocates separate displays for text and graphics, presumably because the standard circuitry would run asynchronously. For example, in Issue 35:

DTACK Grounded, Issue 35, Sep 1984 wrote:
An increasing number of workstation vendors have finally figured out (correctly) that providing a mix of text and graphics on a single monitor is too expensive, and are providing a separate monitor as the primary text output device for menus, etc. If one tries to combine text and graphics onto a single monitor one either pays the price in terms of a slow system, as in Mack's Mack Write program or the old LISA-Write, or you can visit us and try out our Tandy 2000 (sloooow text with the color graphics board installed). Plotting text on a graphics screen like Mack's or the Tandy 2000's is like hitting a racehorse between the eyes with a 5-lb sledge hammer; things essentially come to a halt!


Synchronous output of text and graphics to one display would be very interesting because it would allow rapid fills and unrestricted detail. It would also eliminate separate displays.

plasmo on Tue 4 Jan 2022 wrote:
* How to add sprites.


I understand that the NeoGeo design has a highly unconventional technique. Specifically, it only displayed sprites. I presume this would be implemented with a small double buffer such that one line is rastered while the next is assembled. This arrangement solves a large number of problems including pixel smooth playfields where the foreground moves faster than the background. It is also possible to make a sprite-only system simulate a text-only system.

plasmo on Wed 30 Apr 2022 wrote:
What I need is a program to convert 640x480 picture to hex file that I can load into memory.


I recommend converting bitmaps to uncompressed 8 bit per channel TGA because this format has a fixed length header followed three bytes per pixel. This requires the least effort for further conversion. While you may consider this to be a bodge, the film industry almost exclusively uses 10 bit per channel compressed DPX for similar reasons.

plasmo on Mon 2 May 2022 wrote:
CRC65 has CF mass storage so now is time to think about a filing system for collection of .BMP files so I can retrieve images from CF disk directly.


I've been thinking about suitable images for display. I recommend classic artwork. For Project Snail, I am strongly considering The Snail by Henri Matisse as the default desktop picture. For image compression, I've used pictures of Avril Lavinge as test data because her bold goth/emo style makes errors more apparent. A bold goth/emo style is also compatible with a small palette.

_________________
Modules | Processors | Boards | Boxes | Beep, Beep! I'm a sheep!


Top
 Profile  
Reply with quote  
Display posts from previous:  Sort by  
Post new topic Reply to topic  [ 21 posts ]  Go to page Previous  1, 2

All times are UTC


Who is online

Users browsing this forum: No registered users and 7 guests


You cannot post new topics in this forum
You cannot reply to topics in this forum
You cannot edit your posts in this forum
You cannot delete your posts in this forum
You cannot post attachments in this forum

Search for:
Jump to:  
cron