www.gusucode.com > Arduino_Engineering_Kit_Hardware_Support 工具箱matlab源码程序 > Arduino_Engineering_Kit_Hardware_Support/simulink/+motorcarrier/+blocks/mkrmotorcarrier_Encoder.m
classdef mkrmotorcarrier_Encoder < matlab.System ... & coder.ExternalDependency ... & matlab.system.mixin.Propagates ... & matlab.system.mixin.internal.CustomIcon ... & matlab.system.mixin.internal.SampleTime % % Encoder - MKR Motor Carrier % % Copyright 2018 The MathWorks, Inc. %#codegen %#ok<*EMCA> properties (Nontunable) % Encoder - Encoder Encoder = '1'; % SlaveAddress_ - I2C Slave Address SlaveAddress_ = hex2dec('66'); %SampleTime Sample time SampleTime = 0.1; end properties (Nontunable, Logical) % ShowSpeed - Show Speed output port ShowSpeed = false; % ResetOption - Reset at initialization ResetOption = true; end properties(Constant, Hidden) EncoderSet = matlab.system.StringSet({'1', '2'}); % --------------Commands for Encoder at D11--------------------- GET_RAW_COUNT_ENCODER = 7 ; RESET_COUNT_ENCODER = 8 ; GET_OVERFLOW_UNDERFLOW_STATUS_ENCODER = 9 ; GET_COUNT_PER_SECOND_ENCODER = 10 ; SET_INTERRUPT_ON_COUNT_ENCODER = 11 ; SET_INTERRUPT_ON_VELOCITY_ENCODER = 12 ; end properties (Dependent,Hidden) Encoder_num end methods % Constructor function obj = mkrmotorcarrier_Encoder(varargin) coder.allowpcode('plain'); setProperties(obj,nargin,varargin{:}); end function set.SampleTime(obj,sampleTime) coder.extrinsic('error'); coder.extrinsic('message'); validateattributes(sampleTime,{'numeric'},... {'nonnan', 'finite'},... '','''Sample time'''); % Sample time must be a real scalar value or 2 element array. if ~isreal(sampleTime(1)) || numel(sampleTime) > 2 error(message('arduino:build:InvalidSampleTimeNeedScalar')); end if numel(sampleTime) == 2 && sampleTime(1) > 0.0 && sampleTime(2) >= sampleTime(1) error(message('arduino:build:InvalidSampleTimeNeedSmallerOffset')); end if numel(sampleTime) == 2 && sampleTime(1) == -1.0 && sampleTime(2) ~= 0.0 error(message('arduino:build:InvalidSampleTimeNeedZeroOffset')); end if numel(sampleTime) == 2 && sampleTime(1) == 0.0 && sampleTime(2) ~= 1.0 error(message('arduino:build:InvalidSampleTimeNeedOffsetOne')); end obj.SampleTime = sampleTime; end function val = get.Encoder_num(obj) switch obj.Encoder case '1' val = 0; case '2' val = 1; end end end methods (Access = protected) % Set data in D11 function D11_setData(obj, command, target, data) % Convert int32 data to uint8 (Little Endian by default) data_uint8 = typecast(int32(data), 'uint8'); % Data to write over I2C final_data_to_write = [uint8(command), uint8(target), data_uint8]; if coder.target('Rtw')% done only for code gen coder.cinclude('MW_arduinoI2C.h'); coder.ceval('MW_i2cWriteLoop', uint8(obj.SlaveAddress_), 0, 0, ... coder.rref(final_data_to_write), 6); elseif ( coder.target('RtwForRapid') || coder.target('RtwForSfun') ) end end % Get data from D11 function data = D11_getData(obj, command, target) % First write the command and target over I2C final_data_to_write = [uint8(command), uint8(target)]; % Number of bytes to read num_bytes_to_read = 5; % Allocate out out_raw = coder.nullcopy(uint8(zeros(1, num_bytes_to_read))); if coder.target('Rtw')% done only for code gen coder.cinclude('MW_arduinoI2C.h'); coder.ceval('MW_i2cWriteLoop', uint8(obj.SlaveAddress_), 0, 0, ... coder.rref(final_data_to_write), 2); % Read the 5 bytes (irq_status + int32 data) of data over I2C coder.ceval('MW_i2cReadLoop', uint8(obj.SlaveAddress_),... 0, 0, uint8(num_bytes_to_read), coder.wref(out_raw)); elseif ( coder.target('RtwForRapid') || coder.target('RtwForSfun') ) end % Ignore the first irq_status byte received for the time being out = out_raw(2:end); % Concatenate received bytes to get int32 data data = typecast(out, 'int32'); end function Encoder_resetCounter(obj) D11_setData(obj, uint8(obj.RESET_COUNT_ENCODER),... uint8(obj.Encoder_num), int32(0)); end function out = Encoder_getRawCount(obj) out = D11_getData(obj, uint8(obj.GET_RAW_COUNT_ENCODER),... uint8(obj.Encoder_num)); end function out = Encoder_getCountPerSecond(obj) out = D11_getData(obj, uint8(obj.GET_COUNT_PER_SECOND_ENCODER),... uint8(obj.Encoder_num)); end end methods (Access=protected) function setupImpl(obj) if coder.target('Rtw') % Reset the Encoder count if specified if obj.ResetOption Encoder_resetCounter(obj); end else % Do nothing end end function releaseImpl(~) % Release resources, such as file handles end function varargout = stepImpl(obj) count = int32(0); speed = int32(0); %counts per second if coder.target('Rtw') count = Encoder_getRawCount(obj); if obj.ShowSpeed % Encoder_getCountPerSecond returns counts per % centisecond (0.01s) so multiplication factor of 100 % for counts per second speed = Encoder_getCountPerSecond(obj) * 100; end else % Do nothing end varargout{1} = count; varargout{2} = speed; end end methods (Access=protected) %% Define input properties function num = getNumInputsImpl(~) num = 0; end function num = getNumOutputsImpl(obj) if obj.ShowSpeed num = 2; else num = 1; end end function varargout = getOutputNamesImpl(obj) varargout{1} = 'Position'; if obj.ShowSpeed varargout{2} = 'Speed'; end end function varargout= getOutputSizeImpl(obj) varargout{1} = [1,1]; if obj.ShowSpeed varargout{2} = [1,1]; end end function varargout= getOutputDataTypeImpl(obj) for N = 1 : obj.getNumOutputsImpl varargout{N} = 'int32'; end end function varargout = isOutputComplexImpl(obj) for N = 1 : obj.getNumOutputsImpl varargout{N} = false; end end function varargout = isOutputFixedSizeImpl(obj) for N = 1 : obj.getNumOutputsImpl varargout{N} = true; end end function st = getSampleTimeImpl(obj) st = obj.SampleTime; end function maskDisplayCmds = getMaskDisplayImpl(obj) encoder_name = ['sprintf(''Encoder: %X'',' obj.Encoder ')']; if obj.ShowSpeed names = getOutputNames(obj); output_label = [ ... ['port_label(''output'',1,''', names{1}, ''');',newline], ... ['port_label(''output'',2,''', names{2}, ''');'],... ]; maskDisplayCmds = [ ... ['color(''white'');', newline]... % Fix min and max x,y co-ordinates for autoscale mask units ['plot([100,100,100,100],[100,100,100,100]);', newline]... ['plot([0,0,0,0],[0,0,0,0]);', newline]... ['sppkgroot = strrep(motorcarrier.internal.getSpPkgRootDir(),''\'',''/'');',newline]... ['image(fullfile(sppkgroot,''resources'',''encoder.png''),''center'')',newline]... ['color(''blue'');', newline] ... % Drawing mask layout of the block ['text(99, 92, ''ARDUINO'', ''horizontalAlignment'', ''right'');', newline] ... ['color(''black'');', newline] ... ['text(50,15,' encoder_name ',''horizontalAlignment'', ''center'');', newline], ... output_label ,... ]; else maskDisplayCmds = [ ... ['color(''white'');', newline]... % Fix min and max x,y co-ordinates for autoscale mask units ['plot([100,100,100,100],[100,100,100,100]);', newline]... ['plot([0,0,0,0],[0,0,0,0]);', newline]... ['sppkgroot = strrep(motorcarrier.internal.getSpPkgRootDir(),''\'',''/'');',newline]... ['image(fullfile(sppkgroot,''resources'',''encoder.png''),''center'')',newline]... ['color(''blue'');', newline] ... % Drawing mask layout of the block ['text(99, 92, ''ARDUINO'', ''horizontalAlignment'', ''right'');', newline] ... ['color(''black'');', newline] ... ['text(50,15,' encoder_name ',''horizontalAlignment'', ''center'');', newline], ... ]; end end end methods (Static, Access=protected) function simMode = getSimulateUsingImpl(~) simMode = 'Interpreted execution'; end function isVisible = showSimulateUsingImpl isVisible = false; end function groups = getPropertyGroupsImpl(~) % Define section for properties in System block dialog box. EncoderProp = matlab.system.display.internal.Property(... 'Encoder', 'Description', 'Encoder'); SlaveAddressProp = matlab.system.display.internal.Property(... 'SlaveAddress_', 'IsGraphical', false); ShowSpeedProp = matlab.system.display.internal.Property(... 'ShowSpeed', 'Description', 'Show Speed output port'); ResetOptionProp = matlab.system.display.internal.Property(... 'ResetOption', 'Description', 'Reset count at initialization'); SampleTimeProp = matlab.system.display.internal.Property(... 'SampleTime', 'Description', 'Sample time'); Group = matlab.system.display.Section(... 'Title', 'Parameters', 'PropertyList', ... {EncoderProp, SlaveAddressProp,... ShowSpeedProp, ResetOptionProp,... SampleTimeProp,... }); groups = Group; end % Note that this is ignored for the mask-on-mask function header = getHeaderImpl %getHeaderImpl Create mask header % This only has an effect on the base mask. header = matlab.system.display.Header(mfilename('class'), ... 'Title', 'Encoder', ... 'Text', sprintf('Measure the rotation of a motor in ticks.\n\nThe block outputs the position and rotational speed of the motor. The position is measured in ticks and the speed is measured in ticks per second of int32 datatype.\n\nEvery increment in the tick count indicates a clockwise rotation and every decrement in the tick count indicates a counterclockwise rotation.'), ... 'ShowSourceLink', false); end end methods (Static) function name = getDescriptiveName() name = 'MKR Motor Carrier Encoder'; end function b = isSupportedContext(context) b = context.isCodeGenTarget('rtw'); end function updateBuildInfo(buildInfo, context) if context.isCodeGenTarget('rtw') codertarget.arduinobase.internal.arduinoI2CWrite.updateBuildInfo(buildInfo, context); end end end end