Just doing text to morse code conversion. The source code is not optimised, but it works.
//=========================================================== // FPGA CW Keyer (MAX10 10M08SAE144C8GES) //=========================================================== `define POW_ON_RESET_MAX 16'hffff module FPGA ( input wire CLK48, // pin 27, 48MHz Clock output wire[2:0] LED, // pin [122:120], LED Output [Green, Blue, Red] output wire KEY_OUT // pin 132, CN2-5, key output ); //-------------------------- // Internal Power on Reset //-------------------------- wire reset_n ; // Internal Reset Signal reg pow_on_reset_n ; // power-up level = Low reg [15:0] pow_on_reset_count ; // power-up level = Low always @(posedge CLK48) begin if (pow_on_reset_count != `POW_ON_RESET_MAX) begin pow_on_reset_n <= 1'b0; pow_on_reset_count <= pow_on_reset_count + 16'h0001; end else begin pow_on_reset_n <= 1'b1; pow_on_reset_count <= pow_on_reset_count; end end assign reset_n = pow_on_reset_n; //--------- counter for dot clock --------------------- parameter COUNT_PERIOD = 32'h0010_0000; reg [31:0] count; wire count_up /* synthesis keep */; always @ (posedge CLK48 or negedge reset_n) begin if ( reset_n == 1'b0 ) begin count <= 32'h0000_0000; end else begin if ( count == (COUNT_PERIOD - 32'h0000_0001) ) begin count <= 32'h0000_0000; end else begin count <= count + 32'h0000_0001; end end end assign count_up = ( count == (COUNT_PERIOD - 1) )? 1'b1 : 1'b0; //--------- 10-bit morse code table (7-bit data and 3-bit length) parameter N_CODE = 32; reg [4:0] morse_code; reg [9:0] code_pattern; always @(morse_code) begin case (morse_code) 5'b0_0000: code_pattern <= 10'b01_00000_010; // a 5'b0_0001: code_pattern <= 10'b1000_000_100; // b 5'b0_0010: code_pattern <= 10'b1010_000_100; // c 5'b0_0011: code_pattern <= 10'b100_0000_011; // d 5'b0_0100: code_pattern <= 10'b0_000000_001; // e 5'b0_0101: code_pattern <= 10'b0010_000_100; // f 5'b0_0110: code_pattern <= 10'b110_0000_011; // g 5'b0_0111: code_pattern <= 10'b0000_000_100; // h 5'b0_1000: code_pattern <= 10'b00_00000_010; // i 5'b0_1001: code_pattern <= 10'b0111_000_100; // j 5'b0_1010: code_pattern <= 10'b101_0000_011; // k 5'b0_1011: code_pattern <= 10'b0100_000_100; // l 5'b0_1100: code_pattern <= 10'b11_00000_010; // m 5'b0_1101: code_pattern <= 10'b10_00000_010; // n 5'b0_1110: code_pattern <= 10'b111_0000_011; // o 5'b0_1111: code_pattern <= 10'b0110_000_100; // p 5'b1_0000: code_pattern <= 10'b1101_000_100; // q 5'b1_0001: code_pattern <= 10'b010_0000_011; // r 5'b1_0010: code_pattern <= 10'b000_0000_011; // s 5'b1_0011: code_pattern <= 10'b1_000000_001; // t 5'b1_0100: code_pattern <= 10'b001_0000_011; // u 5'b1_0101: code_pattern <= 10'b0001_000_100; // v 5'b1_0110: code_pattern <= 10'b011_0000_011; // w 5'b1_0111: code_pattern <= 10'b1001_000_100; // x 5'b1_1000: code_pattern <= 10'b1011_000_100; // y 5'b1_1001: code_pattern <= 10'b1100_000_100; // z 5'b1_1010: code_pattern <= 10'b00000_00_101; // 0 5'b1_1011: code_pattern <= 10'b01111_00_101; // 1 5'b1_1100: code_pattern <= 10'b00111_00_101; // 2 5'b1_1101: code_pattern <= 10'b00011_00_101; // 3 5'b1_1110: code_pattern <= 10'b00001_00_101; // 4 5'b1_1111: code_pattern <= 10'b1000101__111; // <BK> default : code_pattern <= 10'b00_00000_000; // default endcase end //--------- morse code state transition and output ------------ reg [3:0] r_state; reg key_out; reg [6:0] shift_reg; reg [2:0] length; always @ (r_state) begin case(r_state) 4'b0000: begin key_out <= 1'b0; end // idle 4'b0001: begin key_out <= 1'b1; end // dash 1 4'b0010: begin key_out <= 1'b1; end // dash 2 4'b0011: begin key_out <= 1'b1; end // dash 3 4'b0100: begin key_out <= 1'b0; end // char space 1 4'b0101: begin key_out <= 1'b1; end // dot 1 4'b0110: begin key_out <= 1'b0; end // word space 1 4'b0111: begin key_out <= 1'b0; end // word space 2 4'b1000: begin key_out <= 1'b0; end 4'b1001: begin key_out <= 1'b0; end 4'b1010: begin key_out <= 1'b0; end 4'b1011: begin key_out <= 1'b0; end 4'b1100: begin key_out <= 1'b0; end 4'b1101: begin key_out <= 1'b0; end 4'b1110: begin key_out <= 1'b0; end 4'b1111: begin key_out <= 1'b0; end endcase end assign KEY_OUT = key_out; always @ (posedge CLK48 or negedge reset_n) begin if ( reset_n == 1'b0 ) begin r_state <= 4'b0000; morse_code <= 5'b0_0000; end else begin if(count_up) begin case (r_state) 4'b0000: begin r_state <= 4'b0001; end 4'b0001: begin r_state <= 4'b0010; end 4'b0010: begin r_state <= 4'b0011; end 4'b0011: begin r_state <= 4'b0100; end 4'b0100: if(length != 3'b000) begin if(shift_reg[5]) // not MSB because before shift begin r_state <= 4'b0001; end else begin r_state <= 4'b0101; end shift_reg <= {shift_reg[5:0], 1'b0}; length <= length - 3'b001; end else begin r_state <= 4'b0110; end 4'b0101: begin r_state <= 4'b0100; end 4'b0110: begin shift_reg <= code_pattern[9:3]; length <= code_pattern[2:0] - 3'b001; if(morse_code == (N_CODE - 1) ) begin morse_code <= 5'b0_0000; end else begin morse_code <= morse_code + 5'b0_0001; end r_state <= 4'b0111; end 4'b0111: begin if(shift_reg[6]) begin r_state <= 4'b0001; end else begin r_state <= 4'b0101; end end default: begin r_state <= r_state; end endcase end else begin r_state <= r_state; end end end //---------------- // LED Output //---------------- reg [2:0] myled ; always @(posedge CLK48, negedge reset_n) begin if (reset_n == 1'b0 ) begin myled <= 3'b001; end else begin myled <= r_state[2:0]; end end assign LED = ~myled; //=========================================================== endmodule //===========================================================