001package jmri.jmrit.logixng.util.parser.functions; 002 003import java.util.ArrayList; 004import java.util.HashSet; 005import java.util.List; 006import java.util.Set; 007 008import jmri.JmriException; 009import jmri.jmrit.logixng.SymbolTable; 010import jmri.jmrit.logixng.util.parser.*; 011import jmri.util.TypeConversionUtil; 012 013import org.openide.util.lookup.ServiceProvider; 014 015/** 016 * Implementation of string functions. 017 * 018 * @author Daniel Bergqvist 2020 019 */ 020@ServiceProvider(service = FunctionFactory.class) 021public class StringFunctions implements FunctionFactory { 022 023 @Override 024 public String getModule() { 025 return "String"; 026 } 027 028 @Override 029 public Set<Function> getFunctions() { 030 Set<Function> functionClasses = new HashSet<>(); 031 032 addFormatFunction(functionClasses); 033 addStrlenFunction(functionClasses); 034 035 return functionClasses; 036 } 037 038 @Override 039 public Set<Constant> getConstants() { 040 return new HashSet<>(); 041 } 042 043 @Override 044 public String getConstantDescription() { 045 // This module doesn't define any constants 046 return null; 047 } 048 049 private void addFormatFunction(Set<Function> functionClasses) { 050 functionClasses.add(new AbstractFunction(this, "format", Bundle.getMessage("String.format_Descr")) { 051 @Override 052 public Object calculate(SymbolTable symbolTable, List<ExpressionNode> parameterList) 053 throws CalculateException, JmriException { 054 if (parameterList.isEmpty()) { 055 throw new WrongNumberOfParametersException(Bundle.getMessage("WrongNumberOfParameters1", getName(), 1)); 056 } 057 058 String formatStr = TypeConversionUtil.convertToString( 059 parameterList.get(0).calculate(symbolTable), false); 060 061 List<Object> list = new ArrayList<>(); 062 for (int i=1; i < parameterList.size(); i++) { 063 list.add(parameterList.get(i).calculate(symbolTable)); 064 } 065 066 return String.format(formatStr, list.toArray()); 067 } 068 }); 069 } 070 071 private void addStrlenFunction(Set<Function> functionClasses) { 072 functionClasses.add(new AbstractFunction(this, "strlen", Bundle.getMessage("String.strlen_Descr")) { 073 @Override 074 public Object calculate(SymbolTable symbolTable, List<ExpressionNode> parameterList) 075 throws CalculateException, JmriException { 076 if (parameterList.size() != 1) { 077 throw new WrongNumberOfParametersException(Bundle.getMessage("WrongNumberOfParameters1", getName(), 1)); 078 } 079 080 Object parameter = parameterList.get(0).calculate(symbolTable); 081 082 if (parameter == null) { 083 throw new NullPointerException("Parameter is null"); 084 } else if (parameter instanceof String) { 085 return ((String)parameter).length(); 086 } 087 088 throw new IllegalArgumentException("Parameter is not a String: "+parameter.getClass().getName()); 089 } 090 }); 091 } 092 093}