function varargout = Mandelbrot(varargin)
% MANDELBROT M-file for Mandelbrot.fig
%      MANDELBROT, by itself, creates a new MANDELBROT or raises the existing
%      singleton*.
%
%      H = MANDELBROT returns the handle to a new MANDELBROT or the handle to
%      the existing singleton*.
%
%      MANDELBROT('CALLBACK',hObject,eventData,handles,...) calls the local
%      function named CALLBACK in MANDELBROT.M with the given input arguments.
%
%      MANDELBROT('Property','Value',...) creates a new MANDELBROT or raises the
%      existing singleton*.  Starting from the left, property value pairs are
%      applied to the GUI before Mandelbrot_OpeningFcn gets called.  An
%      unrecognized property name or invalid value makes property application
%      stop.  All inputs are passed to Mandelbrot_OpeningFcn via varargin.
%
%      *See GUI Options on GUIDE's Tools menu.  Choose "GUI allows only one
%      instance to run (singleton)".
%
% See also: GUIDE, GUIDATA, GUIHANDLES

% Edit the above text to modify the response to help Mandelbrot

% Last Modified by GUIDE v2.5 15-Sep-2008 08:01:59

% Begin initialization code - DO NOT EDIT
gui_Singleton = 1;
gui_State = struct('gui_Name',       mfilename, ...
                   'gui_Singleton',  gui_Singleton, ...
                   'gui_OpeningFcn', @Mandelbrot_OpeningFcn, ...
                   'gui_OutputFcn',  @Mandelbrot_OutputFcn, ...
                   'gui_LayoutFcn',  [] , ...
                   'gui_Callback',   []);
if nargin && ischar(varargin{1})
    gui_State.gui_Callback = str2func(varargin{1});
end

if nargout
    [varargout{1:nargout}] = gui_mainfcn(gui_State, varargin{:});
else
    gui_mainfcn(gui_State, varargin{:});
end
% End initialization code - DO NOT EDIT


% --- Executes just before Mandelbrot is made visible.
function Mandelbrot_OpeningFcn(hObject, eventdata, handles, varargin)
% This function has no output args, see OutputFcn.
% hObject    handle to figure
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
% varargin   command line arguments to Mandelbrot (see VARARGIN)


handles.image_size=400;

handles.iteration_max=100;
handles.scale_factor=100;
handles.center_real_hold=0;
handles.center_real=0;
handles.center_imaginary_hold=0;
handles.center_imaginary=0;

handles.center_change=0;
handles.scale_change=0;

handles.show_axes=0;
handles.scale_orbit=0;
handles.scale_iterations=0;

handles.real_values=(1:handles.image_size);
handles.imaginary_values=(1:handles.image_size);
handles.pts_complex_plane=zeros([handles.image_size handles.image_size]);
handles.ptvalues=zeros([handles.image_size handles.image_size 3]);

handles.figure_handle = 1;


    for j=1:handles.image_size
        for i=1:handles.image_size
            handles.ptvalues(j,i,1)=(sin(pi*i/handles.image_size))^2;
            handles.ptvalues(j,i,2)=(cos(pi*i/50*handles.image_size))^2*(cos(pi*j/handles.image_size))^2;
            handles.ptvalues(j,i,3)=(sin(pi*j/(2*handles.image_size)))^2;
        end
    end
    
    
img=(handles.ptvalues);
    
    handles.image_handle = image(handles.real_values, handles.imaginary_values, img);
    %axis image        % Set aspect ratio to obtain square pixels
    set(handles.slider_imaginary_center, 'value', 0.5);
    set(handles.slider_real_center, 'value', 0.5);

handles.filename_image='No File Selected';


% Choose default command line output for Mandelbrot
handles.output = hObject;

% Update handles structure
guidata(hObject, handles);

% UIWAIT makes Mandelbrot wait for user response (see UIRESUME)
% uiwait(handles.figure1);


% --- Outputs from this function are returned to the command line.
function varargout = Mandelbrot_OutputFcn(hObject, eventdata, handles) 
% varargout  cell array for returning output args (see VARARGOUT);
% hObject    handle to figure
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)

% Get default command line output from handles structure
varargout{1} = handles.output;

%/////////////////BUTTONS///////////////////////////////////////

% --- Executes on button press in button_save_image.
function button_save_image_Callback(hObject, eventdata, handles)
% hObject    handle to button_save_image (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
dr2 = uigetdir(' ', 'Choose a Directory to Save the Image to.');
    namehere=['mandelbrot_re' mat2str(handles.center_real) '_im_' mat2str(handles.center_imaginary) '_mag_' mat2str(handles.scale_factor)] ;
    namehere(logical(namehere==' '))='_';
    namehere(logical(namehere=='\'))='-';
    fsname=[dr2 '\' namehere '.bmp'];
    
    imwrite(handles.ptvalues, fsname, 'bmp');


% --- Executes on button press in button_magnify.
function button_magnify_Callback(hObject, eventdata, handles)
% hObject    handle to button_magnify (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
handles.scale_factor=2*handles.scale_factor;
set(handles.edit_info_scale_factor, 'string', mat2str(handles.scale_factor));
guidata(hObject, handles);

% --- Executes on button press in button_demagnify.
function button_demagnify_Callback(hObject, eventdata, handles)
% hObject    handle to button_demagnify (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
handles.scale_factor=handles.scale_factor/2;
if handles.scale_factor < 100;   
    handles.scale_factor = 100;    
end
set(handles.edit_info_scale_factor, 'string', mat2str(handles.scale_factor));
guidata(hObject, handles);


% --- Executes on button press in button_show_image.
function button_show_image_Callback(hObject, eventdata, handles)
% hObject    handle to button_show_image (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)

handles.center_imaginary = handles.center_imaginary_hold;
handles.center_real = handles.center_real_hold;
%Fill in x and y values
for cn=1:handles.image_size
    handles.real_values(cn)=handles.center_real+(cn-handles.image_size/2)/handles.scale_factor;
    handles.imaginary_values(cn)=handles.center_imaginary-(cn-handles.image_size/2)/handles.scale_factor;
end

for rlcnt=1:handles.image_size
    for imcnt=1:handles.image_size
        iterations=0;
        attractor=0;
        z=0+0*i;
        c=handles.real_values(rlcnt)+i*handles.imaginary_values(imcnt);
        while (iterations < handles.iteration_max && attractor < 2)
            z=z*z+c;
            iterations=iterations+1;
            attractor=z*conj(z);
        end %(while)
        if (get(handles.radio_color,'Value') == get(handles.radio_color,'Max'))%in color?
            %if iterations == handles.iteration_max % inside the set
            if attractor <= 2 % inside the set
            if handles.scale_orbit == 1 %scale by orbit?
                  handles.ptvalues(imcnt, rlcnt, 1)=(attractor/2);
                    handles.ptvalues(imcnt, rlcnt, 2)=(0.9*attractor/2);
                        handles.ptvalues(imcnt, rlcnt, 3)=0;
              else %just make it RED
                  handles.ptvalues(imcnt, rlcnt, 1)=0.3;
                    handles.ptvalues(imcnt, rlcnt, 2)=0.2;
                        handles.ptvalues(imcnt, rlcnt, 3)=0.1;
              end
            else % outside the set
            
              if handles.scale_iterations == 1 %Scale by iterations
                  handles.ptvalues(imcnt, rlcnt, 1)=(0.0);
                    handles.ptvalues(imcnt, rlcnt, 2)=(1*iterations/handles.iteration_max);
                        handles.ptvalues(imcnt, rlcnt, 3)=(1-0.9*iterations/handles.iteration_max);
              else %just make it white
                  handles.ptvalues(imcnt, rlcnt, 1)=1;
                    handles.ptvalues(imcnt, rlcnt, 2)=1;
                        handles.ptvalues(imcnt, rlcnt, 3)=1;
              end
        end
        else %then black and white
        %if iterations == handles.iteration_max % inside the set
        if attractor <= 2 % inside the set
            
              if handles.scale_orbit == 1 %scale by orbit?
                  handles.ptvalues(imcnt, rlcnt, 1)=(0.42*attractor);
                    handles.ptvalues(imcnt, rlcnt, 2)=(0.42*attractor);
                        handles.ptvalues(imcnt, rlcnt, 3)=(0.42*attractor);
                        
              else %just make it black
                  handles.ptvalues(imcnt, rlcnt, 1)=0;
                    handles.ptvalues(imcnt, rlcnt, 2)=0;
                        handles.ptvalues(imcnt, rlcnt, 3)=0;
              end
        else % outside the set
            
              if handles.scale_iterations == 1 %yes scale by iterations for the non set
                  handles.ptvalues(imcnt, rlcnt, 1)=(1-0.78*iterations/handles.iteration_max);
                    handles.ptvalues(imcnt, rlcnt, 2)=(1-0.78*iterations/handles.iteration_max);
                        handles.ptvalues(imcnt, rlcnt, 3)=(1-0.78*iterations/handles.iteration_max);
              else %Just make non set white
                  handles.ptvalues(imcnt, rlcnt, 1)=1;
                    handles.ptvalues(imcnt, rlcnt, 2)=1;
                        handles.ptvalues(imcnt, rlcnt, 3)=1;
              end
        end
        if handles.show_axes == 1
            if handles.real_values(rlcnt) == 0 || handles.imaginary_values(imcnt) == 0
                handles.ptvalues(imcnt, rlcnt, 1)=0;
                handles.ptvalues(imcnt, rlcnt, 2)=0;
                handles.ptvalues(imcnt, rlcnt, 3)=0;
            end
        end
        end
    end
end

img=(handles.ptvalues);
    
    handles.image_handle = image(img, 'XData', handles.real_values, 'YData', handles.imaginary_values);
    xlabel x; ylabel iy;
    axis xy 
    %axis image       % Set aspect ratio to obtain square pixels
    set(handles.slider_imaginary_center, 'value', 0.5);
    set(handles.slider_real_center, 'value', 0.5);
    
    guidata(hObject, handles);

%/////////////////END BUTTONS//////////////////////////////////////



%////////////////TEXT EDITS///////////////////////////////////////

function edit_info_scale_factor_Callback(hObject, eventdata, handles)
% hObject    handle to edit_info_scale_factor (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
user_entry = str2double(get(hObject,'string'));
if isnan(user_entry)
	errordlg('You must enter a numeric value','Bad Input','modal')
    set(hObject, 'string', mat2str(handles.scale_factor));
	return
else
    handles.scale_factor=user_entry;
    if user_entry < 100
        handles.scale_factor=100;
    end
    
    guidata(hObject, handles);
    set(hObject, 'string', mat2str(handles.scale_factor));
    handles.scale_change=1;
    
end

% Hints: get(hObject,'String') returns contents of edit_info_scale_factor as text
%        str2double(get(hObject,'String')) returns contents of edit_info_scale_factor as a double
guidata(hObject, handles);

% --- Executes during object creation, after setting all properties.
function edit_info_scale_factor_CreateFcn(hObject, eventdata, handles)
% hObject    handle to edit_info_scale_factor (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.
%       See ISPC and COMPUTER.
if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor','white');
end



function edit_center_real_Callback(hObject, eventdata, handles)
% hObject    handle to edit_center_real (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
user_entry = str2double(get(hObject,'string'));
handles.center_real = handles.center_real_hold;
if isnan(user_entry)
	errordlg('You must enter a numeric value','Bad Input','modal')
    set(hObject, 'string', mat2str(handles.center_real));
	return
else
    handles.center_real=user_entry;
    if user_entry < -4
        handles.center_real=-4;
    end
    if user_entry > 4
        handles.center_real=4; 
    end
    
    handles.center_real_hold = handles.center_real;
    guidata(hObject, handles);
    set(hObject, 'string', mat2str(handles.center_real));
    handles.center_change=1;
end

% Hints: get(hObject,'String') returns contents of edit_center_real as text
%        str2double(get(hObject,'String')) returns contents of edit_center_real as a double
guidata(hObject, handles);

% --- Executes during object creation, after setting all properties.
function edit_center_real_CreateFcn(hObject, eventdata, handles)
% hObject    handle to edit_center_real (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.
%       See ISPC and COMPUTER.
if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor','white');
end



function edit_center_imaginary_Callback(hObject, eventdata, handles)
% hObject    handle to edit_center_imaginary (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
user_entry = str2double(get(hObject,'string'));
handles.center_imaginary = handles.center_imaginary_hold;
if isnan(user_entry)
	errordlg('You must enter a numeric value','Bad Input','modal')
    set(hObject, 'string', mat2str(handles.center_imaginary));
	return
else
    handles.center_imaginary=user_entry;
    if user_entry < -4
        handles.center_imaginary=-4;
    end
    if user_entry > 4
        handles.center_imaginary=4; 
    end
    
    handles.center_imaginary_hold = handles.center_imaginary;
    guidata(hObject, handles);
    set(hObject, 'string', mat2str(handles.center_imaginary));
    handles.center_change=1;
end
% Hints: get(hObject,'String') returns contents of edit_center_imaginary as text
%        str2double(get(hObject,'String')) returns contents of edit_center_imaginary as a double
guidata(hObject, handles);

% --- Executes during object creation, after setting all properties.
function edit_center_imaginary_CreateFcn(hObject, eventdata, handles)
% hObject    handle to edit_center_imaginary (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.
%       See ISPC and COMPUTER.
if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor','white');
end



function edit_iteration_limit_Callback(hObject, eventdata, handles)
% hObject    handle to edit_iteration_limit (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
user_entry = str2double(get(hObject,'string'));
if isnan(user_entry)
	errordlg('You must enter a numeric value','Bad Input','modal')
    set(hObject, 'string', mat2str(handles.iteration_max));
	return
else
    handles.iteration_max=user_entry;
    if user_entry < 100
        handles.iteration_max=100;
    end
    if user_entry > 1000000
        handles.iteration_max=1000000; 
    end
    
    guidata(hObject, handles);
    set(hObject, 'string', mat2str(handles.iteration_max));
    
end
% Hints: get(hObject,'String') returns contents of edit_iteration_limit as text
%        str2double(get(hObject,'String')) returns contents of edit_iteration_limit as a double
guidata(hObject, handles);

% --- Executes during object creation, after setting all properties.
function edit_iteration_limit_CreateFcn(hObject, eventdata, handles)
% hObject    handle to edit_iteration_limit (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: edit controls usually have a white background on Windows.
%       See ISPC and COMPUTER.
if ispc && isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor','white');
end


%////////////////////END TEXT EDITS/////////////////////////////////////

%/////////////////CHECK BOXES/////////////////////////////////////////

% --- Executes on button press in checkbox_axes.
function checkbox_axes_Callback(hObject, eventdata, handles)
% hObject    handle to checkbox_axes (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
handles.show_axes=get(hObject, 'Value');
% Hint: get(hObject,'Value') returns toggle state of checkbox_axes
guidata(hObject, handles);

% --- Executes on button press in checkbox_orbit.
function checkbox_orbit_Callback(hObject, eventdata, handles)
% hObject    handle to checkbox_orbit (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
handles.scale_orbit=get(hObject, 'Value');
% Hint: get(hObject,'Value') returns toggle state of checkbox_orbit
guidata(hObject, handles);

% --- Executes on button press in checkbox_iteration.
function checkbox_iteration_Callback(hObject, eventdata, handles)
% hObject    handle to checkbox_iteration (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
handles.scale_iterations=get(hObject, 'Value');
% Hint: get(hObject,'Value') returns toggle state of checkbox_iteration
guidata(hObject, handles);

%//////////////////////END CHECK BOXES///////////////////////////////

%///////////////// SLIDERS //////////////////////////////////////////


% --- Executes on slider movement.
function slider_imaginary_center_Callback(hObject, eventdata, handles)
% hObject    handle to slider_imaginary_center (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
slider_imaginary_center = get(hObject,'Value');
handles.center_imaginary_hold=handles.center_imaginary+((slider_imaginary_center*(handles.image_size-1)+1)-handles.image_size/2)/handles.scale_factor;
  


set(hObject, 'value', slider_imaginary_center);
guidata(hObject, handles);
set(handles.edit_center_imaginary, 'string', mat2str(handles.center_imaginary_hold));


% Hints: get(hObject,'Value') returns position of slider
%        get(hObject,'Min') and get(hObject,'Max') to determine range of slider


% --- Executes during object creation, after setting all properties.
function slider_imaginary_center_CreateFcn(hObject, eventdata, handles)
% hObject    handle to slider_imaginary_center (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: slider controls usually have a light gray background.
if isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor',[.9 .9 .9]);
end


% --- Executes on slider movement.
function slider_real_center_Callback(hObject, eventdata, handles)
% hObject    handle to slider_real_center (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    structure with handles and user data (see GUIDATA)
slider_real_center = get(hObject,'Value');
handles.center_real_hold=handles.center_real+((slider_real_center*(handles.image_size-1)+1)-handles.image_size/2)/handles.scale_factor;
  


set(hObject, 'value', slider_real_center);
guidata(hObject, handles);
set(handles.edit_center_real, 'string', mat2str(handles.center_real_hold));
% Hints: get(hObject,'Value') returns position of slider
%        get(hObject,'Min') and get(hObject,'Max') to determine range of slider


% --- Executes during object creation, after setting all properties.
function slider_real_center_CreateFcn(hObject, eventdata, handles)
% hObject    handle to slider_real_center (see GCBO)
% eventdata  reserved - to be defined in a future version of MATLAB
% handles    empty - handles not created until after all CreateFcns called

% Hint: slider controls usually have a light gray background.
if isequal(get(hObject,'BackgroundColor'), get(0,'defaultUicontrolBackgroundColor'))
    set(hObject,'BackgroundColor',[.9 .9 .9]);
end

%/////////////////END SLIDERS//////////////////////////////////////////

%/////////////////END FILE//////////////////////////////////////////
