Skip to content

Commit 3f84a8e

Browse files
astururclaude
andcommitted
feat: add OSD H/V image centering offsets (+/-8 px/lines)
Shifts the active image by repartitioning the native timing's front and back porches; H_TOTAL/V_TOTAL stay fixed so the CRT keeps the same line and frame rate. V blanking rebalanced from 6/3/13 to 8/3/11 to give a symmetric +/-8 budget without changing refresh rate. Co-Authored-By: Claude Opus 4.7 <noreply@anthropic.com>
1 parent ef38ec1 commit 3f84a8e

3 files changed

Lines changed: 39 additions & 9 deletions

File tree

menu.sv

Lines changed: 15 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -208,10 +208,16 @@ assign LED_POWER[0]= FB ? led[2] : act_cnt2[26] ? act_cnt2[25:18] > act_cnt2[7:0
208208

209209

210210
`include "build_id.v"
211+
// Image centering: 4-bit signed in OSD ordering 0,+1..+7,-8..-1 so that the
212+
// power-on default (status bits = 0) maps to "no shift". Bit pattern matches
213+
// 4-bit two's complement when reinterpreted as signed.
211214
localparam CONF_STR = {
212215
"MENU;UART31250,MIDI;",
213216
"-;",
214-
"V,v",`BUILD_DATE
217+
"O[13:10],H Offset,0,+1,+2,+3,+4,+5,+6,+7,-8,-7,-6,-5,-4,-3,-2,-1;",
218+
"O[17:14],V Offset,0,+1,+2,+3,+4,+5,+6,+7,-8,-7,-6,-5,-4,-3,-2,-1;",
219+
"-;",
220+
"V,v",`BUILD_DATE
215221
};
216222

217223
wire forced_scandoubler;
@@ -514,7 +520,14 @@ native_video_top native_video
514520
.vga_vcount (native_vcount),
515521
.vga_new_frame (native_new_frame),
516522
.enable (mode_zaparoo),
517-
.active (native_active)
523+
.active (native_active),
524+
525+
// status[13:10] / status[17:14] are 4-bit fields whose bit pattern
526+
// matches signed two's complement when the OSD enum is ordered
527+
// 0,+1..+7,-8..-1 (see CONF_STR). $signed() makes the reinterpretation
528+
// explicit at the port boundary.
529+
.h_offset ($signed(status[13:10])),
530+
.v_offset ($signed(status[17:14]))
518531
);
519532

520533
// Cosine + LFSR fallback noise pattern, painted into the 320x240 active area

rtl/native_video_timing.sv

Lines changed: 17 additions & 6 deletions
Original file line numberDiff line numberDiff line change
@@ -1,11 +1,18 @@
11
// Zaparoo native video timing: 320x240 at 15.734 kHz from 27 MHz / 4.
2+
// h_offset/v_offset (signed -8..+7) shift the image by repartitioning
3+
// front porch and back porch. H_TOTAL/V_TOTAL are invariant, so line
4+
// rate and frame rate are unchanged regardless of offset values.
25

36
module native_video_timing
47
(
58
input wire clk,
69
input wire ce_pix,
710
input wire reset,
811

12+
// Image centering: positive = shift right/down (FP shrinks, BP grows).
13+
input wire signed [3:0] h_offset, // -8..+7 pixels (budget H_FP=14 / H_BP=63)
14+
input wire signed [3:0] v_offset, // -8..+7 lines (budget V_FP=8 / V_BP=11)
15+
916
output reg hsync,
1017
output reg vsync,
1118
output reg hblank,
@@ -23,16 +30,20 @@ localparam [5:0] H_SYNC = 6'd32;
2330
localparam [9:0] H_BP = 10'd63;
2431
localparam [9:0] H_TOTAL = 10'd429;
2532

33+
// V blanking rebalanced from 6/3/13 to 8/3/11 to give symmetric ±8 budget
34+
// while preserving V_TOTAL=262 (and thus 59.94 Hz refresh).
2635
localparam [8:0] V_ACTIVE = 9'd240;
27-
localparam [8:0] V_FP = 9'd6;
36+
localparam [8:0] V_FP = 9'd8;
2837
localparam [4:0] V_SYNC = 5'd3;
29-
localparam [8:0] V_BP = 9'd13;
38+
localparam [8:0] V_BP = 9'd11;
3039
localparam [8:0] V_TOTAL = 9'd262;
3140

32-
localparam [9:0] H_SYNC_START = H_ACTIVE + H_FP;
33-
localparam [9:0] H_SYNC_END = H_SYNC_START + H_SYNC;
34-
localparam [8:0] V_SYNC_START = V_ACTIVE + V_FP;
35-
localparam [8:0] V_SYNC_END = V_SYNC_START + V_SYNC;
41+
// Sync starts shift with the offset; two's-complement subtraction in
42+
// unsigned arithmetic yields the correct result at both ends of the range.
43+
wire [9:0] H_SYNC_START = H_ACTIVE + (H_FP - {{6{h_offset[3]}}, h_offset});
44+
wire [9:0] H_SYNC_END = H_SYNC_START + H_SYNC;
45+
wire [8:0] V_SYNC_START = V_ACTIVE + (V_FP - {{5{v_offset[3]}}, v_offset});
46+
wire [8:0] V_SYNC_END = V_SYNC_START + V_SYNC;
3647

3748
always @(posedge clk) begin
3849
if(reset) begin

rtl/native_video_top.sv

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -29,7 +29,11 @@ module native_video_top
2929
output wire vga_new_frame,
3030

3131
input wire enable,
32-
output wire active
32+
output wire active,
33+
34+
// OSD image centering: signed -8..+7 pixels/lines, 0 = no shift.
35+
input wire signed [3:0] h_offset,
36+
input wire signed [3:0] v_offset
3337
);
3438

3539
wire tim_hs;
@@ -46,6 +50,8 @@ native_video_timing timing
4650
.clk (clk_vid),
4751
.ce_pix (ce_pix),
4852
.reset (reset),
53+
.h_offset (h_offset),
54+
.v_offset (v_offset),
4955
.hsync (tim_hs),
5056
.vsync (tim_vs),
5157
.hblank (tim_hblank),

0 commit comments

Comments
 (0)