image thumbnail
from Tromino by Krishna Lalith
Can you fill the 4x4 Checker Board with set of L-Shaped Trominoes???

Tromino(action)
function Tromino(action)
%----------------------------------------------------------------------
%INTRODUCTION:
%The inspiration of this game is from Mathematical Problem/Puzzle.

%This Math Problem is very famous and mostly used in Mathematical Induction
%and also in Algorithm Lectures (hence Number Theory).

%I have choosen only 4x4 Chess Board as it is very critical/important step in 
%Mathematical Induction.

%Other higher levels of the Puzzle will be repetition of 4x4 levels
%and hence not much of fun.

%The intention of the game is to appreciate the capability of Mathematical
%Induction (not GUI of the game) for problems that look very complicated 
%but results in simple solution.

%The solution using Congruence Modulo is, for 2^k x 2^k case (= 4^k), the
%congruence modulo division by 3 (L-Shaped Tromino has 3 unit squares)
%is always 1^k (= 1).
%----------------------------------------------------------------------
global L_Tri L_Tri_count Current_Link;
global CX CY CC fig OriX OriY;
clc;
%--------------------------------------------------------------------------
if nargin < 1, 
    L_Tri=zeros(4,4);  
    L_Tri_count=1; 
    Current_Link=ones(2,2);
    Current_Link(1+mod(fix(10*rand(1,1)),2),1+mod(fix(10*rand(1,1)),2))=0;
     
    fig=figure( ...
                'Name','Tromino', 'NumberTitle','off', ...
                'Visible','off', 'BackingStore','off');         
    %----------------------------------------------------------------------
    % Handling the handles
            
    uicontrol('units','normalized',...
                'position',[.8 .61 .07  .05],'string','Help', ...
                'callback','Tromino(''Help'')', ...
                'interruptible','on','BackgroundColor','w');
            
    uicontrol('units','normalized',...
                'position',[.8 .53 .07  .05],'string','Reset', ...
                'callback','Tromino(''Reset'')', ...
                'interruptible','on','BackgroundColor','w');
           
    uicontrol('units','normalized',...
                'position',[.8 .45 .07  .05],'string','Theory', ...
                'callback','Tromino(''Theory'')', ...
                'interruptible','on','BackgroundColor','w');

    uicontrol('units','normalized',...
                'position',[.8 .37 .07  .05],'string','Exit', ...
                'callback','delete(gcf)', ...
                'interruptible','on','BackgroundColor','w');
    
    uicontrol('units','normalized',...
                'position',[.49 .18 .06  .05],'string','Fix', ...
                'callback','Tromino(''Fix'')', ...
                'interruptible','on','BackgroundColor',[1 0.6 0.3]);
            
    uicontrol('units','normalized',...
                'position',[.49 .26 .06  .05],'string','Up', ...
                'callback','Tromino(''Up'')', ...
                'interruptible','on','BackgroundColor',[0 0.6 1]);
            
    uicontrol('units','normalized',...
                'position',[.49 .10 .06  .05],'string','Down', ...
                'callback','Tromino(''Down'')', ...
                'interruptible','on','BackgroundColor',[0 0.6 1]);
           
    uicontrol('units','normalized',...
                'position',[.57 .18 .06  .05],'string','Right', ...
                'callback','Tromino(''Right'')', ...
                'interruptible','on','BackgroundColor',[0 0.6 0.4]);

    uicontrol('units','normalized',...
                'position',[.41 .18 .06  .05],'string','Left', ...
                'callback','Tromino(''Left'')', ...
                'interruptible','on','BackgroundColor',[0 0.6 0.4]);
            
    uicontrol('units','normalized',...
                'position',[.65 .18 .06  .05],'string','CWR', ...
                'callback','Tromino(''CWR'')', ...
                'interruptible','on','BackgroundColor',[1 0.4 0.6]);
           
    uicontrol('units','normalized',...
                'position',[.33 .18 .06  .05],'string','CCWR', ...
                'callback','Tromino(''CCWR'')', ...
                'interruptible','on','BackgroundColor',[1 0.4 0.6]);
    
    action='Start';
end
%--------------------------------------------------------------------------
if strcmp(action,'Start')
    %4x4 Chess Board
    OriX=-1;  OriY=-1;
    CX=0;  CY=4;  
    CC=[0.9 0.99 0.9;0.99 0.9 0.9;0.9 0.9 0.99;0.7 0.8 0.9;1 1 1];
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
    figure(fig);
end
%--------------------------------------------------------------------------
if strcmp(action,'Help')
    msg=strvcat('DESCRIPTION of GAME:                                          ',...
                ' ',... 
                '1. Use L-Shaped Trominoes to fill 4x4 Chess Board.            ',...                
                '2. Use directions for [Linear] or (Angular) movements.        ',...
                '3. Press "Theory" button to know the theory behind this puzzle',...
                '    (preferrably at the end of the game).                     ');
     
    msgbox(msg,'Tromino Help','help');
end
%--------------------------------------------------------------------------
if strcmp(action,'Reset') 
    closereq;
    Tromino();
end
%--------------------------------------------------------------------------
if strcmp(action,'Theory')
    msg=strvcat('Theory behind the Puzzle:                              ',...
                ' ',... 
                'For any generalized case, say 2^k x 2^k Chess Board,   ',...                     
                '    using (a) Mathematical Induction or (b) Congruence Modulo',...
                '    (Number Theory) the puzzle always lead to one unfilled unit square.');
     
    msgbox(msg,'Tromino Theory','help');    
end
%--------------------------------------------------------------------------
if strcmp(action,'Exit') 
    closereq;
end
%--------------------------------------------------------------------------
if strcmp(action,'Up')
    CY=CY+1;
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'Down')
    CY=CY-1;
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'Right')
    CX=CX+1; 
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'Left')
    CX=CX-1;
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'Fix')      
    fixit=0;
    if (CX-1+OriX>0 && CX-1+OriX<5 && CY+OriY>0 && CY+OriY<5), 
        if (L_Tri(CX-1+OriX,CY+OriY)==0),   fixit=fixit+1;  end
    end
    if (CX+OriX>0 && CX+OriX<5 && CY+OriY>0 && CY+OriY<5),
        if (L_Tri(CX+OriX,CY+OriY)==0),     fixit=fixit+1;  end
    end
    if (CX-1+OriX>0 && CX-1+OriX<5 && CY-1+OriY>0 && CY-1+OriY<5),
        if (L_Tri(CX-1+OriX,CY-1+OriY)==0), fixit=fixit+1;  end
    end
    if (CX+OriX>0 && CX+OriX<5 && CY-1+OriY>0 && CY-1+OriY<5),
        if (L_Tri(CX+OriX,CY-1+OriY)==0),   fixit=fixit+1;  end
    end
            
    if fixit>=3,        
        %fixing the link 
        L_Tri(CX-1+OriX,CY+OriY)    = L_Tri_count*Current_Link(1,1) + L_Tri(CX-1+OriX,CY+OriY);
        L_Tri(CX+OriX,CY+OriY)      = L_Tri_count*Current_Link(1,2) + L_Tri(CX+OriX,CY+OriY);
        L_Tri(CX-1+OriX,CY-1+OriY)  = L_Tri_count*Current_Link(2,1) + L_Tri(CX-1+OriX,CY-1+OriY);
        L_Tri(CX+OriX,CY-1+OriY)    = L_Tri_count*Current_Link(2,2) + L_Tri(CX+OriX,CY-1+OriY);
                   
        CX=0;  CY=4;
        L_Tri_count=L_Tri_count+1;
        
        %checking for the possibilities
        valid=Check_L_Tri(L_Tri);
        if valid==0 && L_Tri_count>4,
            msg='No possibility of Placement of L-Tromino...';
            msg_handle=msgbox(msg,'Try Again!','error');
            if ~waitforbuttonpress,  close(msg_handle);  end
            Tromino('Prompt');
        else        
            if L_Tri_count>5,  Tromino('Prompt');
            else
                axes('Units','normalized','Visible','off',...
                 'DrawMode','fast','NextPlot','add'); 
                axes('Units','normalized','Visible','off',...
                 'DrawMode','fast','NextPlot','replace');
                Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
                Board();
            end
        end
    end
end
%--------------------------------------------------------------------------
if strcmp(action,'CCWR')
    Current_Link=rot90(Current_Link);
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'CWR')
    Current_Link=rot90(Current_Link,-1);
    Update(CX,CY,Current_Link,CC(L_Tri_count,:)); 
    Board();
end
%--------------------------------------------------------------------------
if strcmp(action,'Prompt')
    [namastedata namastemap]=imread('namaste.jpg');
    msg={'Game is Over...'};
    msg_handle=msgbox(msg,'Good Try...!','custom',namastedata,namastemap);        
    if ~waitforbuttonpress,  close(msg_handle);  end

    PlayAgain='y';
    PlayAgain = inputdlg({'Want to Play Again???'},'PlayAgain',1,{PlayAgain});
    if strcmp(PlayAgain,'y'),
        Tromino('Reset');
    else
        closereq;
        Tromino('Exit');       
    end
end
%--------------------------------------------------------------------------

Contact us at files@mathworks.com