Base: BD-J Adjustments Blu-ray scaffold
Vendored BD-J SDK, tsMuxeR + local VLC plugins, ffmpeg asset generation, and a signed BD-J Xlet menu (org.homebrew.MyXlet) authored into a UDF 2.50 ISO. Co-Authored-By: Claude Opus 4.8 <noreply@anthropic.com>
This commit is contained in:
commit
9c88b8f7f6
110 changed files with 19469 additions and 0 deletions
160
src/org/homebrew/AdjustmentsMenu.java
Normal file
160
src/org/homebrew/AdjustmentsMenu.java
Normal file
|
|
@ -0,0 +1,160 @@
|
|||
package org.homebrew;
|
||||
|
||||
import java.awt.Color;
|
||||
import java.awt.Container;
|
||||
import java.awt.Font;
|
||||
import java.awt.FontMetrics;
|
||||
import java.awt.Graphics;
|
||||
import java.awt.event.KeyEvent;
|
||||
import java.awt.event.KeyListener;
|
||||
|
||||
public class AdjustmentsMenu extends Container implements KeyListener {
|
||||
private static final String[] MAIN_ITEMS = {
|
||||
"MAIN FEATURE",
|
||||
"BONUS: WAITING ROOM OUTTAKES",
|
||||
"BONUS: CLAIM DENIED",
|
||||
"SETTINGS"
|
||||
};
|
||||
|
||||
private static final String[] HIDDEN_ITEMS = {
|
||||
"DELETED FORM 13-B",
|
||||
"THE BASEMENT MENU",
|
||||
"COMPLIANCE CONFESSIONAL",
|
||||
"RETURN"
|
||||
};
|
||||
|
||||
private final Font titleFont = new Font("SansSerif", Font.BOLD, 62);
|
||||
private final Font itemFont = new Font("SansSerif", Font.BOLD, 28);
|
||||
private final Font smallFont = new Font("SansSerif", Font.PLAIN, 18);
|
||||
private int selected = 0;
|
||||
private boolean hidden;
|
||||
private int codeProgress;
|
||||
private String status = "BD-J scaffold loaded";
|
||||
|
||||
public AdjustmentsMenu() {
|
||||
setFocusable(true);
|
||||
}
|
||||
|
||||
public void paint(Graphics g) {
|
||||
int w = getWidth();
|
||||
int h = getHeight();
|
||||
String[] items = hidden ? HIDDEN_ITEMS : MAIN_ITEMS;
|
||||
|
||||
g.setColor(new Color(8, 8, 10));
|
||||
g.fillRect(0, 0, w, h);
|
||||
|
||||
drawBars(g, w, h);
|
||||
|
||||
g.setFont(titleFont);
|
||||
g.setColor(new Color(245, 245, 230));
|
||||
g.drawString("ADJUSTMENTS", 78, 120);
|
||||
|
||||
g.setFont(smallFont);
|
||||
g.setColor(new Color(167, 201, 190));
|
||||
g.drawString(hidden ? "UNFILED MATERIALS" : "MAIN MENU", 84, 160);
|
||||
|
||||
for (int i = 0; i < items.length; i++) {
|
||||
int y = 250 + (i * 58);
|
||||
boolean isSelected = i == selected;
|
||||
|
||||
if (isSelected) {
|
||||
g.setColor(new Color(183, 40, 48));
|
||||
g.fillRect(74, y - 34, 510, 44);
|
||||
g.setColor(new Color(255, 248, 220));
|
||||
} else {
|
||||
g.setColor(new Color(202, 202, 190));
|
||||
}
|
||||
|
||||
g.setFont(itemFont);
|
||||
g.drawString(items[i], 96, y);
|
||||
}
|
||||
|
||||
g.setFont(smallFont);
|
||||
g.setColor(new Color(125, 125, 118));
|
||||
g.drawString(status, 82, h - 78);
|
||||
|
||||
drawStamp(g, w, h);
|
||||
}
|
||||
|
||||
private void drawBars(Graphics g, int w, int h) {
|
||||
g.setColor(new Color(22, 28, 30));
|
||||
for (int i = 0; i < 12; i++) {
|
||||
int x = (i * 137) % w;
|
||||
g.fillRect(x, 0, 8, h);
|
||||
}
|
||||
|
||||
g.setColor(new Color(178, 40, 47));
|
||||
g.fillRect(0, h - 34, w, 8);
|
||||
g.setColor(new Color(48, 112, 102));
|
||||
g.fillRect(0, h - 24, w, 6);
|
||||
}
|
||||
|
||||
private void drawStamp(Graphics g, int w, int h) {
|
||||
String copy = hidden ? "UNAPPROVED" : "TEMPORARY";
|
||||
g.setFont(new Font("SansSerif", Font.BOLD, 30));
|
||||
FontMetrics metrics = g.getFontMetrics();
|
||||
int textWidth = metrics.stringWidth(copy);
|
||||
|
||||
g.setColor(new Color(52, 52, 48));
|
||||
g.drawRect(w - 312, 72, 230, 82);
|
||||
g.drawRect(w - 306, 78, 218, 70);
|
||||
g.setColor(new Color(183, 40, 48));
|
||||
g.drawString(copy, w - 198 - (textWidth / 2), 124);
|
||||
}
|
||||
|
||||
private void activate() {
|
||||
String[] items = hidden ? HIDDEN_ITEMS : MAIN_ITEMS;
|
||||
String item = items[selected];
|
||||
|
||||
if (hidden && selected == HIDDEN_ITEMS.length - 1) {
|
||||
hidden = false;
|
||||
selected = 0;
|
||||
status = "Returned to approved materials";
|
||||
} else if ("MAIN FEATURE".equals(item)) {
|
||||
status = "Main feature is playlist 00000";
|
||||
} else if ("SETTINGS".equals(item)) {
|
||||
status = "Settings stub selected";
|
||||
} else {
|
||||
status = item + " stub selected";
|
||||
}
|
||||
|
||||
repaint();
|
||||
}
|
||||
|
||||
private void unlockHidden() {
|
||||
hidden = true;
|
||||
selected = 0;
|
||||
codeProgress = 0;
|
||||
status = "Hidden menu unlocked";
|
||||
repaint();
|
||||
}
|
||||
|
||||
public void keyPressed(KeyEvent e) {
|
||||
int code = e.getKeyCode();
|
||||
String[] items = hidden ? HIDDEN_ITEMS : MAIN_ITEMS;
|
||||
|
||||
if (code == KeyEvent.VK_UP) {
|
||||
selected = (selected + items.length - 1) % items.length;
|
||||
repaint();
|
||||
} else if (code == KeyEvent.VK_DOWN) {
|
||||
selected = (selected + 1) % items.length;
|
||||
repaint();
|
||||
} else if (code == KeyEvent.VK_ENTER || code == KeyEvent.VK_SPACE) {
|
||||
activate();
|
||||
} else if (code == KeyEvent.VK_6 || e.getKeyChar() == '6') {
|
||||
codeProgress++;
|
||||
if (codeProgress >= 3) {
|
||||
unlockHidden();
|
||||
}
|
||||
} else {
|
||||
codeProgress = 0;
|
||||
}
|
||||
}
|
||||
|
||||
public void keyReleased(KeyEvent e) {
|
||||
}
|
||||
|
||||
public void keyTyped(KeyEvent e) {
|
||||
}
|
||||
}
|
||||
|
||||
64
src/org/homebrew/MyXlet.java
Normal file
64
src/org/homebrew/MyXlet.java
Normal file
|
|
@ -0,0 +1,64 @@
|
|||
package org.homebrew;
|
||||
|
||||
import java.awt.BorderLayout;
|
||||
import javax.tv.xlet.Xlet;
|
||||
import javax.tv.xlet.XletContext;
|
||||
import javax.tv.xlet.XletStateChangeException;
|
||||
import org.havi.ui.HScene;
|
||||
import org.havi.ui.HSceneFactory;
|
||||
|
||||
public class MyXlet extends Thread implements Xlet {
|
||||
private HScene scene;
|
||||
private AdjustmentsMenu menu;
|
||||
private boolean running;
|
||||
|
||||
public void initXlet(XletContext context) throws XletStateChangeException {
|
||||
menu = new AdjustmentsMenu();
|
||||
menu.setSize(1280, 720);
|
||||
|
||||
scene = HSceneFactory.getInstance().getDefaultHScene();
|
||||
scene.add(menu, BorderLayout.CENTER);
|
||||
scene.addKeyListener(menu);
|
||||
scene.validate();
|
||||
scene.repaint();
|
||||
}
|
||||
|
||||
public void startXlet() throws XletStateChangeException {
|
||||
running = true;
|
||||
menu.setVisible(true);
|
||||
scene.setVisible(true);
|
||||
menu.requestFocus();
|
||||
scene.requestFocus();
|
||||
start();
|
||||
}
|
||||
|
||||
public void pauseXlet() {
|
||||
if (menu != null) {
|
||||
menu.setVisible(false);
|
||||
}
|
||||
}
|
||||
|
||||
public void destroyXlet(boolean unconditional) {
|
||||
running = false;
|
||||
interrupt();
|
||||
|
||||
if (scene != null && menu != null) {
|
||||
menu.setVisible(false);
|
||||
scene.remove(menu);
|
||||
}
|
||||
|
||||
scene = null;
|
||||
menu = null;
|
||||
}
|
||||
|
||||
public void run() {
|
||||
while (running) {
|
||||
try {
|
||||
Thread.sleep(1000);
|
||||
} catch (InterruptedException e) {
|
||||
running = false;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
4
src/org/homebrew/bluray.MyXlet.perm
Normal file
4
src/org/homebrew/bluray.MyXlet.perm
Normal file
|
|
@ -0,0 +1,4 @@
|
|||
grant {
|
||||
permission java.security.AllPermission;
|
||||
};
|
||||
|
||||
Loading…
Add table
Add a link
Reference in a new issue