Skip to content

Update LCD4Linux #9

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 5 commits into from
Feb 7, 2025
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
128 changes: 71 additions & 57 deletions lcd4linux/src/Photoframe.py
Original file line number Diff line number Diff line change
Expand Up @@ -5,11 +5,12 @@
from usb.util import get_string
from PIL import Image
from struct import pack
from six import ensure_binary
from six.moves import cStringIO as StringIO


def write_jpg2frame(dev, pic):
"""Attach header to picture, pad with zeros if necessary, and send to frame"""
# Attach header to picture, pad with zeros if necessary, and send to frame
# create header and stack before picture
# middle 4 bytes have size of picture
rawdata = b"\xa5\x5a\x18\x04" + pack('<I', len(pic) + 14) + b"\x48\x00\x00\x00" + pic
Expand All @@ -22,95 +23,96 @@ def write_jpg2frame(dev, pic):


def get_known_devices():
"""Return a dict of photo frames"""
dList = []
# Return a dict of photo frames
dlist = []
# listed as: Name, idVendor, idProduct, [width , height - in pixel if applicable]
#

#0,1 Samsung SPF-75H/76H (23)
dList.append({'name': "SPF75H/76H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200f, 'width': 800, 'height': 480})
dList.append({'name': "SPF75H/76H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200e})
dlist.append({'name': "SPF75H/76H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200f, 'width': 800, 'height': 480})
dlist.append({'name': "SPF75H/76H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200e})

#2,3 Samsung SPF-87H (24)
dList.append({'name': "SPF87H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2034, 'width': 800, 'height': 480})
dList.append({'name': "SPF87H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2033})
dlist.append({'name': "SPF87H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2034, 'width': 800, 'height': 480})
dlist.append({'name': "SPF87H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2033})

#4,5 Samsung SPF-87Hold (25)
dList.append({'name': "SPF87Hold Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2026, 'width': 800, 'height': 480})
dList.append({'name': "SPF87Hold Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2025})
dlist.append({'name': "SPF87Hold Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2026, 'width': 800, 'height': 480})
dlist.append({'name': "SPF87Hold Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2025})

#6,7 Samsung SPF-83H (26)
dList.append({'name': "SPF83H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200d, 'width': 800, 'height': 600})
dList.append({'name': "SPF83H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200c})
dlist.append({'name': "SPF83H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200d, 'width': 800, 'height': 600})
dlist.append({'name': "SPF83H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200c})

#8,9 Samsung SPF-107H (27)
dList.append({'name': "SPF107H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2036, 'width': 1024, 'height': 600})
dList.append({'name': "SPF107H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2035})
dlist.append({'name': "SPF107H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2036, 'width': 1024, 'height': 600})
dlist.append({'name': "SPF107H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2035})

#10,11 Samsung SPF-105P (28)
dList.append({'name': "SPF105P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x201b, 'width': 1024, 'height': 600})
dList.append({'name': "SPF105P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x201c})
dlist.append({'name': "SPF105P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x201b, 'width': 1024, 'height': 600})
dlist.append({'name': "SPF105P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x201c})

#12,13 Samsung SPF-85H/86H (29)
dList.append({'name': "SPF85H/86H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2013, 'width': 800, 'height': 600})
dList.append({'name': "SPF85H/86H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2012})
dlist.append({'name': "SPF85H/86H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2013, 'width': 800, 'height': 600})
dlist.append({'name': "SPF85H/86H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2012})

#14,15 Samsung SPF-72H (210)
dList.append({'name': "SPF72H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200b, 'width': 800, 'height': 480})
dList.append({'name': "SPF72H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200a})
dlist.append({'name': "SPF72H Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x200b, 'width': 800, 'height': 480})
dlist.append({'name': "SPF72H Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x200a})

#16,17 Samsung SPF-700T (211)
dList.append({'name': "SPF700T Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2050, 'width': 800, 'height': 600})
dList.append({'name': "SPF700T Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x204f})
dlist.append({'name': "SPF700T Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2050, 'width': 800, 'height': 600})
dlist.append({'name': "SPF700T Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x204f})

#18,19 Samsung SPF-85P/86P (212)
dList.append({'name': "SPF85P/86P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2017, 'width': 800, 'height': 600})
dList.append({'name': "SPF85P/86P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2016})
dlist.append({'name': "SPF85P/86P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2017, 'width': 800, 'height': 600})
dlist.append({'name': "SPF85P/86P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2016})

#20,21 Samsung SPF-107Hold (213)
dList.append({'name': "SPF107Hold Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2028, 'width': 1024, 'height': 600})
dList.append({'name': "SPF107Hold Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2027})
dlist.append({'name': "SPF107Hold Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2028, 'width': 1024, 'height': 600})
dlist.append({'name': "SPF107Hold Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2027})

#22,23 Samsung SPF-1000P (214)
dList.append({'name': "SPF1000P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2040, 'width': 1024, 'height': 600})
dList.append({'name': "SPF1000P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2039})
dlist.append({'name': "SPF1000P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2040, 'width': 1024, 'height': 600})
dlist.append({'name': "SPF1000P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2039})

#24,25 Samsung SPF-800P (215)
dList.append({'name': "SPF800P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2038, 'width': 800, 'height': 480})
dList.append({'name': "SPF800P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2037})
dlist.append({'name': "SPF800P Mini Monitor", 'idVendor': 0x04e8, 'idProduct': 0x2038, 'width': 800, 'height': 480})
dlist.append({'name': "SPF800P Mass Storage", 'idVendor': 0x04e8, 'idProduct': 0x2037})

# Amazon Fire 7 (9th Generation 2019)
dlist.append({'name': "Amazon Fire 7 Mini Monitor", 'idVendor': 0x1949, 'idProduct': 0x03C3, 'width': 1024, 'height': 600})
dlist.append({'name': "Amazon Fire 7 Mass Storage", 'idVendor': 0x1949, 'idProduct': 0x03C1})

# Pearl DPF for Testing
dList.append({'name': "Pearl DPF", 'idVendor': 0x1908, 'idProduct': 0x0102, 'width': 320, 'height': 240})
dList.append({'name': "Pearl DPF", 'idVendor': 0x1908, 'idProduct': 0x0102, 'width': 320, 'height': 240})
dlist.append({'name': "Pearl DPF", 'idVendor': 0x1908, 'idProduct': 0x0102, 'width': 320, 'height': 240})
dlist.append({'name': "Pearl DPF", 'idVendor': 0x1908, 'idProduct': 0x0102, 'width': 320, 'height': 240})

return dList
return dlist


def find_device(Anzahl, device, device2):
"""Try to find device on USB bus."""
def find_device(anzahl, device, device2):
# Try to find device on USB bus.
try:
print("[LCD4linux] looking for frame", Anzahl, device['name'], device['idVendor'], device['idProduct'], device2['idProduct'])
if Anzahl == 2:
print("[LCD4linux] looking for frame", anzahl, device['name'], device['idVendor'], device['idProduct'], device2['idProduct'])
if anzahl == 2:
d = list(find(idVendor=device['idVendor'], idProduct=device['idProduct'], find_all=True)) + list(find(idVendor=device2['idVendor'], idProduct=device2['idProduct'], find_all=True))
if isinstance(d, list):
if len(d) >= 2:
d = d[1]
else:
d = None
d = d[1] if len(d) >= 2 else None
else:
d = None
else:
d = list(list(find(idVendor=device['idVendor'], idProduct=device['idProduct'], find_all=True)) + list(find(idVendor=device2['idVendor'], idProduct=device2['idProduct'], find_all=True)))[0]
except:
except Exception:
from traceback import format_exc
print("[LCD4linux] find exception")
print("Error: %s" % format_exc())
d = None
return d


def init_device(Anzahl, device0, device1):
"""First try Mini Monitor mode, then Mass storage mode"""
dev = find_device(Anzahl, device0, device1)
def init_device(anzahl, device0, device1):
# First try Mini Monitor mode, then Mass storage mode
dev = find_device(anzahl, device0, device1)

if dev is not None:
## found it, trying to init it
Expand All @@ -124,7 +126,7 @@ def init_device(Anzahl, device0, device1):
ts = time()
while True:
# may need to burn some time
dev = find_device(Anzahl, device0, device1)
dev = find_device(anzahl, device0, device1)
if dev is not None and dev.idProduct == device0["idProduct"]:
#switching successful
break
Expand All @@ -140,46 +142,58 @@ def init_device(Anzahl, device0, device1):


def frame_init(dev):
"""Init device so it stays in Mini Monitor mode"""
# Init device so it stays in Mini Monitor mode
# this is the minimum required to keep the frame in Mini Monitor mode!!!
# dev.ctrl_transfer(0xc0, 4 )
# dev.ctrl_transfer(0xc0, 0x01, 0x00, 0x00, 0x09, 0x04 )
# dev.ctrl_transfer(0xc0, 4 )
# dev.ctrl_transfer(0xc0, 0x01, 0x00, 0x00, 0x09, 0x04 )
dev.ctrl_transfer(0xc0, 0x01, 0x00, 0x00, 0x02)


def frame_switch(dev):
"""Switch device from Mass Storage to Mini Monitor"""
# Switch device from Mass Storage to Mini Monitor
CTRL_TYPE_VENDOR = (2 << 5)
CTRL_IN = 0x80
CTRL_RECIPIENT_DEVICE = 0
try:
sleep(0.5)
s = "\x00" * 251
dev.ctrl_transfer(0x00 | 0x80, 0x06, 0xfe, 0xfe, 0xfe)
except:
# dev.ctrl_transfer(0x00 | 0x80, 0x06, 0xfe, 0xfe, s, 0xfe )
# dev.ctrl_transfer(CTRL_TYPE_VENDOR | CTRL_IN | CTRL_RECIPIENT_DEVICE, 0x04, 0x00, 0x00, 1)
# result = dev.ctrl_transfer(CTRL_TYPE_VENDOR | CTRL_IN | CTRL_RECIPIENT_DEVICE, 0x04, 0x00, 0x00, 1)
# expect(result, [ 0x03 ])
# result = dev.ctrl_transfer(CTRL_TYPE_VENDOR | CTRL_IN | CTRL_RECIPIENT_DEVICE, 0x01, 0x00, 0x00, 2)
# expect(result, [ 0x09, 0x04 ])
# result = dev.ctrl_transfer(CTRL_TYPE_VENDOR | CTRL_IN | CTRL_RECIPIENT_DEVICE, 0x02, 0x00, 0x00, 1)
# expect(result, [ 0x46 ])
# settling of the bus and frame takes about 0.42 sec
# give it some extra time, but then still make sure it has settled
except Exception:
print("[LCD4linux] switching ERROR")
# from traceback import format_exc
# print format_exc()
finally:
sleep(2)


def name(dev):
try:
return get_string(dev, 1)
except:
except Exception:
try:
return get_string(dev, 256, 2)
except:
except Exception:
return None


def main():
global dev, known_devices_list

known_devices_list = get_known_devices()

# define which frame to use, here use Samsung SPF-87H
device0 = known_devices_list[0] # Mini Monitor mode
device1 = known_devices_list[1] # Mass Storage mode

dev = init_device(1, device0, device1)
print("Frame is in Mini Monitor mode and initialized. Sending pictures now")

image = Image.open("mypicture.jpg")
#manipulations to consider:
# convert
Expand Down
12 changes: 6 additions & 6 deletions lcd4linux/src/dpf.py
Original file line number Diff line number Diff line change
Expand Up @@ -2,7 +2,7 @@
from six import PY2
try:
from . import dpflib
except:
except Exception:
print("[LCD4linux] dpflib-Error")

PROPERTY_BRIGHTNESS = 0x01
Expand All @@ -15,7 +15,7 @@ def setBacklight(dev, value):
try:
dev.setProperty(PROPERTY_BRIGHTNESS, value)
return True
except:
except Exception:
print("[LCD4linux] Error set Backlight")
return False

Expand All @@ -29,17 +29,17 @@ def showImage(dev, image):
else:
dev.showRGBAImage(0, 0, x, y, ir.tobytes())
return True
except:
except Exception:
print("[LCD4linux] Error writing DPF Device")
return False


def open(usb):
try:
d = dpflib.open(usb)
d.setProperty(PROPERTY_ORIENTATION, 1)
# d.setProperty(PROPERTY_ORIENTATION, 1)
print("[LCD4linux] open %s" % usb)
except:
except Exception:
d = None
print("[LCD4linux] open Error: %s" % usb)
return d
Expand All @@ -49,5 +49,5 @@ def close(dev):
try:
if dev is not None:
dev.close()
except:
except Exception:
pass
26 changes: 12 additions & 14 deletions lcd4linux/src/module.py
Original file line number Diff line number Diff line change
Expand Up @@ -79,14 +79,14 @@ def getHold(self):
return L4Lelement.Hold

def setHold(self, H):
print("[LCD4linuxE] Hold: %s" % H)
print("[LCD4linuxE] hold: %s" % H)
L4Lelement.Hold = H

def getHoldKey(self):
return L4Lelement.HoldKey

def setHoldKey(self, H=False):
print("[LCD4linuxE] HoldKey: %s" % H)
print("[LCD4linuxE] holdkey: %s" % H)
L4Lelement.HoldKey = H

def getFont(self, F="0"):
Expand All @@ -102,29 +102,27 @@ def getScreen(self):
return L4Lelement.Screen

def setScreen(self, S, Lcd="", Hold=False):
if Lcd != "":
if len(str(Lcd)) > 1 or int(Lcd) > 3:
Lcd = "1"
if Lcd != "" and (len(str(Lcd)) > 1 or int(Lcd) > 3):
Lcd = "1"
L4Lelement.Screen = str(S)
L4Lelement.LCD = str(Lcd)
L4Lelement.Hold = Hold
L4Lelement.Refresh = True

def resetBrightness(self, AKT=""):
def resetBrightness(self, AKT=[]):
if len(AKT) == 3:
L4Lelement.BrightAkt = AKT
else:
L4Lelement.Bright = [-1, -1, -1]

def setBrightness(self, LCD, BRI=-1):
if int(LCD) < 1 or int(LCD) > 3:
return
L4Lelement.Bright[int(LCD) - 1] = int(BRI)
L4Lelement.Refresh = True
if int(LCD) > 0 and int(LCD) < 4:
L4Lelement.Bright[int(LCD) - 1] = int(BRI)
L4Lelement.Refresh = True

def getBrightness(self, LCD=0, ORG=True):
if int(LCD) > 0 and int(LCD) < 4:
return L4Lelement.Bright[int(LCD) - 1] if ORG == False else L4Lelement.BrightAkt[int(LCD) - 1]
return [L4Lelement.Bright[int(LCD) - 1]] if ORG == False else [L4Lelement.BrightAkt[int(LCD) - 1]]
else:
return L4Lelement.Bright if ORG == False else L4Lelement.BrightAkt

Expand All @@ -145,14 +143,13 @@ def getstatusoutput(cmd):
sts = pipe.close()
if sts is None:
sts = 0
if text[-1:] == '\n':
if text.endswith == '\n':
text = text[:-1]
except Exception:
sts = 1
text = "- -"
print("[LCD4linux] Error on os-call")
finally:
return sts, text
return sts, text


def L4LVtest(VV):
Expand All @@ -172,6 +169,7 @@ def L4LVtest(VV):
if O != "":
try:
f = open(L4Linfo % (O, P))
B = f.readline()
OO = f.readline().strip().split()[1].startswith(VV[1:])
f.close()
except Exception:
Expand Down
Loading
Loading