Update sys. HV-Integer scale. Vertical crop.

This commit is contained in:
sorgelig
2021-03-02 20:11:28 +08:00
parent 17fc907348
commit 2c2b476975
11 changed files with 559 additions and 180 deletions

View File

@ -1,6 +1,6 @@
//
//
// Copyright (c) 2017 Sorgelig
// Copyright (c) 2017,2021 Alexey Melnikov
//
// This program is GPL Licensed. See COPYING for the full license.
//
@ -15,8 +15,6 @@
// May be less if line_start is used.
//
// HALF_DEPTH: If =1 then color dept is 4 bits per component
// For half depth 8 bits monochrome is available with
// mono signal enabled and color = {G, R}
//
// altera message_off 10720
// altera message_off 12161
@ -28,32 +26,21 @@ module video_mixer
parameter GAMMA = 0
)
(
// video clock
// it should be multiple by (ce_pix*4).
input clk_vid,
input CLK_VIDEO, // should be multiple by (ce_pix*4)
output reg CE_PIXEL, // output pixel clock enable
// Pixel clock or clock_enable (both are accepted).
input ce_pix,
output ce_pix_out,
input ce_pix, // input pixel clock or clock_enable
input scandoubler,
input hq2x, // high quality 2x scaling
// scanlines (00-none 01-25% 10-50% 11-75%)
input [1:0] scanlines,
// High quality 2x scaling
input hq2x,
inout [21:0] gamma_bus,
// color
input [DWIDTH:0] R,
input [DWIDTH:0] G,
input [DWIDTH:0] B,
// Monochrome mode (for HALF_DEPTH only)
input mono,
inout [21:0] gamma_bus,
// Positive pulses.
input HSync,
input VSync,
@ -75,9 +62,9 @@ localparam HALF_DEPTH_SD = GAMMA ? 0 : HALF_DEPTH;
generate
if(GAMMA && HALF_DEPTH) begin
wire [7:0] R_in = mono ? {G,R} : {R,R};
wire [7:0] G_in = mono ? {G,R} : {G,G};
wire [7:0] B_in = mono ? {G,R} : {B,B};
wire [7:0] R_in = {R,R};
wire [7:0] G_in = {G,G};
wire [7:0] B_in = {B,B};
end else begin
wire [DWIDTH:0] R_in = R;
wire [DWIDTH:0] G_in = G;
@ -95,7 +82,7 @@ generate
assign gamma_bus[21] = 1;
gamma_corr gamma(
.clk_sys(gamma_bus[20]),
.clk_vid(clk_vid),
.clk_vid(CLK_VIDEO),
.ce_pix(ce_pix),
.gamma_en(gamma_bus[19]),
@ -122,7 +109,6 @@ generate
end
endgenerate
wire [DWIDTH_SD:0] R_sd;
wire [DWIDTH_SD:0] G_sd;
wire [DWIDTH_SD:0] B_sd;
@ -130,7 +116,10 @@ wire hs_sd, vs_sd, hb_sd, vb_sd, ce_pix_sd;
scandoubler #(.LENGTH(LINE_LENGTH), .HALF_DEPTH(HALF_DEPTH_SD)) sd
(
.*,
.clk_vid(CLK_VIDEO),
.hq2x(hq2x),
.ce_pix(ce_pix),
.hs_in(hs_g),
.vs_in(vs_g),
.hb_in(hb_g),
@ -149,90 +138,55 @@ scandoubler #(.LENGTH(LINE_LENGTH), .HALF_DEPTH(HALF_DEPTH_SD)) sd
.b_out(B_sd)
);
wire [DWIDTH_SD:0] rt = (scandoubler ? R_sd : R_gamma);
wire [DWIDTH_SD:0] gt = (scandoubler ? G_sd : G_gamma);
wire [DWIDTH_SD:0] bt = (scandoubler ? B_sd : B_gamma);
wire [DWIDTH_SD:0] rt = (scandoubler ? R_sd : R_gamma);
wire [DWIDTH_SD:0] gt = (scandoubler ? G_sd : G_gamma);
wire [DWIDTH_SD:0] bt = (scandoubler ? B_sd : B_gamma);
generate
if(!GAMMA && HALF_DEPTH) begin
wire [7:0] r = mono ? {gt,rt} : {rt,rt};
wire [7:0] g = mono ? {gt,rt} : {gt,gt};
wire [7:0] b = mono ? {gt,rt} : {bt,bt};
end else begin
wire [7:0] r = rt;
wire [7:0] g = gt;
wire [7:0] b = bt;
end
endgenerate
wire hs = (scandoubler ? hs_sd : hs_g);
wire vs = (scandoubler ? vs_sd : vs_g);
assign ce_pix_out = scandoubler ? ce_pix_sd : ce_pix;
reg scanline = 0;
always @(posedge clk_vid) begin
reg old_hs, old_vs;
old_hs <= hs;
old_vs <= vs;
if(old_hs && ~hs) scanline <= ~scanline;
if(old_vs && ~vs) scanline <= 0;
end
wire hde = scandoubler ? ~hb_sd : ~hb_g;
wire vde = scandoubler ? ~vb_sd : ~vb_g;
reg [7:0] v_r,v_g,v_b;
reg v_vs,v_hs,v_de;
always @(posedge clk_vid) begin
always @(posedge CLK_VIDEO) begin
reg [7:0] r,g,b;
reg hde,vde,hs,vs, old_vs;
reg old_hde;
reg old_ce;
reg ce_osc, fs_osc;
old_ce <= ce_pix;
ce_osc <= ce_osc | (old_ce ^ ce_pix);
if(ce_pix_out) begin
case(scanlines & {scanline, scanline})
1: begin // reduce 25% = 1/2 + 1/4
v_r <= {1'b0, r[7:1]} + {2'b00, r[7:2]};
v_g <= {1'b0, g[7:1]} + {2'b00, g[7:2]};
v_b <= {1'b0, b[7:1]} + {2'b00, b[7:2]};
end
old_vs <= vs;
if(~old_vs & vs) begin
fs_osc <= ce_osc;
ce_osc <= 0;
end
2: begin // reduce 50% = 1/2
v_r <= {1'b0, r[7:1]};
v_g <= {1'b0, g[7:1]};
v_b <= {1'b0, b[7:1]};
end
CE_PIXEL <= scandoubler ? ce_pix_sd : fs_osc ? (~old_ce & ce_pix) : ce_pix;
3: begin // reduce 75% = 1/4
v_r <= {2'b00, r[7:2]};
v_g <= {2'b00, g[7:2]};
v_b <= {2'b00, b[7:2]};
end
if(!GAMMA && HALF_DEPTH) begin
r <= {rt,rt};
g <= {gt,gt};
b <= {bt,bt};
end
else begin
r <= rt;
g <= gt;
b <= bt;
end
default: begin
v_r <= r;
v_g <= g;
v_b <= b;
end
endcase
hde <= scandoubler ? ~hb_sd : ~hb_g;
vde <= scandoubler ? ~vb_sd : ~vb_g;
vs <= scandoubler ? vs_sd : vs_g;
hs <= scandoubler ? hs_sd : hs_g;
v_vs <= vs;
v_hs <= hs;
if(CE_PIXEL) begin
VGA_R <= r;
VGA_G <= g;
VGA_B <= b;
VGA_VS <= vs;
VGA_HS <= hs;
old_hde <= hde;
if(~old_hde && hde) v_de <= vde;
if(old_hde && ~hde) v_de <= 0;
if(old_hde ^ hde) VGA_DE <= vde & hde;
end
end
always @(posedge clk_vid) if(ce_pix_out) begin
VGA_R <= v_r;
VGA_G <= v_g;
VGA_B <= v_b;
VGA_HS <= v_hs;
VGA_VS <= v_vs;
VGA_DE <= v_de;
end
endmodule