Code covered by the BSD License  

Highlights from
extracthelp

extracthelp

by

 

13 Sep 2008 (Updated )

Extract the help information of all M functions in a sub-folder

extracthelp(folderName, copyRight)
% EXTRACTHELP Extract the help lines of all files in the current directory
%
% Creates a sub-folder in the current folder and for each .m file in the
% current folder creates a corresponding file in the destination folder
% containing only the first commented lines (i.e., help of the function).
%
% Caution: If the specified folder and M-files already exist they will be
% overwritten.
%
% extracthelp()
% extracthelp(folderName)
% extracthelp(folderName, copyRight)
%
% folderName - folder name where to create the help-files. Default: 'phelp'
% copyRight  - specify whether the copyright lines should be exported as
%              well. Default: true
%
% The comment's extraction starts from the first % sign in the file and
% stops at the first non-commented line. By default the function allows for
% one empty line between the first and the second comment blocks, since
% normally the second comment block contains the copyright information. To
% extract only the help shown by the help function use:
% extracthelp(folderName, false)
%
% The function is useful together with 'pcode', which generates pre-parsed
% files that hide the algorithms inside and therefore are suitable for
% distributing a proprietary software to third parties. However, the
% so-generated files do not contain help information. This can be fixed
% using extracthelp, as shown in the example below.
%
% Example
%  extracthelp()       % create the .\phelp folder and the help files
%                      % for all files in the current folder
%  pcode *.m           % convert all .M files to .P files
%  movefile('*.p','.\phelp')
%  % The phelp folder contains now the files you can now safely distribute
%
% See also  pcode

% This function is distributed under GPL and BSD licenses
% Original authors information:
% Andrey Popov          andrey.popov@gmx.net
% Last update: 2013-07-04

% Copyright (c) 2008, 2013 Andrey Popov
% All rights reserved.
%
% Redistribution and use in source and binary forms, with or without
% modification, are permitted provided that the following conditions are
% met:
%
%     * Redistributions of source code must retain the above copyright
%       notice, this list of conditions and the following disclaimer.
%     * Redistributions in binary form must reproduce the above copyright
%       notice, this list of conditions and the following disclaimer in
%       the documentation and/or other materials provided with the distribution
%
% THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
% AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
% IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
% ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE
% LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
% CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
% SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
% INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
% CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
% ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
% POSSIBILITY OF SUCH DAMAGE.

function extracthelp(folderName, copyRight)

if nargin < 1
    folderName = 'phelp';
end
if nargin < 2
    copyRight = true;
end

commentSign = 37;

% End Of Line settings
EOL = 10;  % EOL is LF
EOL_offset = 1;

% % Alternative settings
% EOL = 13;  % EOL is CR
% EOL_offset = 2;


if isunix
    % You might need to adjust them for your distribution!
    fSep = '/';                        % folder separator sign
    mkdir(folderName);                 % create the destination folder
else
    try
        if ismac
            fSep = '/';
            mkdir(folderName);
        else % PC
            fSep = '\';
            mkdir(folderName);
        end
    catch % older version of Matlab. Try the PC options
        fSep = '\';
        mkdir(folderName);
    end
end
D = dir;

if ~copyRight
    % Do not extract the copyrights (i.e., stop extracting comments at the
    % first non-commented line)
    CRb = sprintf('\n ');   CRe = sprintf('\n');    % carrige return

    for ind = 1:size(D,1)
        if ~D(ind).isdir
            DN = D(ind).name;
            if strcmpi(DN(end-1:end),'.m')
                F = fopen([pwd fSep folderName fSep DN],'w+');
                B = help(DN);
                B = strrep(B,CRb,[CRe '%']);
                B = ['%' B(2:end)];
                fwrite(F,B);
                fclose(F);
            end
        end
    end
    return  % all done
end


% Extract also the 2nd commented block
% (if there are no code-lines in between)

% Iterate over files
for ind = 1:size(D,1)
    if D(ind).isdir,
        continue
    end

    % get only M-files
    DN = D(ind).name;
    if ~strcmpi(DN(end-1:end),'.m')
        continue
    end

    % Open
    H = fopen(DN,'r');
    if H < 0,
        error('EH:fopenH','Could not open source file %s',DN)
    end

    F = fopen([pwd fSep folderName fSep DN],'w+');
    if F < 0;
        fclose(F);
        error('EH:fopenF','Could not open destination %s',DN)
    end

    % Read files
    data = fread(H);
    ma = length(data);
    
    % Find first comment
    a1 = find(data==commentSign,1,'first');

    % If no comments - close and continue
    if a1 == 0
        fclose(F);
        fclose(H);
        continue;
    end
        
    % Ignore everything before the first comment
    data  = data(a1:ma);
    ma = length(data);
    ae = ma;

    % Find the line breaks
    aind = find(data==EOL);
    one_free_line = false;

    % Iterate over lines
    for ix = 1:length(aind)
		
		% Next line is also comment
        if data(min(aind(ix)+EOL_offset,ma)) == commentSign
            % do nothing
        
		elseif data(min(aind(ix)+1,ma)) == EOL || data(min(aind(ix)+2,ma)) == EOL || data(min(aind(ix)+3,ma)) == EOL
            % Next line is empty
            if ~one_free_line
                one_free_line = true;
            else
                % End of comment block + copyright
                ae = aind(ix);
                break
            end
        
		else
            % Normal end of comment block
            ae = aind(ix);
            break
        end
    end

    B = data(1:ae);
    fwrite(F,B);

    fclose(F);
    fclose(H);
end

end % extract help

Contact us