当前位置: 首页>>代码示例>>C++>>正文


C++ NDAttribute类代码示例

本文整理汇总了C++中NDAttribute的典型用法代码示例。如果您正苦于以下问题:C++ NDAttribute类的具体用法?C++ NDAttribute怎么用?C++ NDAttribute使用的例子?那么, 这里精选的类代码示例或许可以为您提供帮助。


在下文中一共展示了NDAttribute类的15个代码示例,这些例子默认根据受欢迎程度排序。您可以为喜欢或者感觉有用的代码点赞,您的评价将有助于系统推荐出更棒的C++代码示例。

示例1: calculateTrigger

asynStatus NDPluginCircularBuff::calculateTrigger(NDArray *pArray, int *trig)
{
    NDAttribute *trigger;
    char triggerString[256];
    double triggerValue;
    double calcResult;
    int status;
    int preTrigger, postTrigger, currentImage, triggered;
    static const char *functionName="calculateTrigger";
    
    *trig = 0;
    
    getIntegerParam(NDCircBuffPreTrigger,   &preTrigger);
    getIntegerParam(NDCircBuffPostTrigger,  &postTrigger);
    getIntegerParam(NDCircBuffCurrentImage, &currentImage);
    getIntegerParam(NDCircBuffTriggered,    &triggered);   

    triggerCalcArgs_[0] = epicsNAN;
    triggerCalcArgs_[1] = epicsNAN;
    triggerCalcArgs_[2] = preTrigger;
    triggerCalcArgs_[3] = postTrigger;
    triggerCalcArgs_[4] = currentImage;
    triggerCalcArgs_[5] = triggered;

    getStringParam(NDCircBuffTriggerA, sizeof(triggerString), triggerString);
    trigger = pArray->pAttributeList->find(triggerString);
    if (trigger != NULL) {
        status = trigger->getValue(NDAttrFloat64, &triggerValue);
        if (status == asynSuccess) {
            triggerCalcArgs_[0] = triggerValue;
        }
    }
    getStringParam(NDCircBuffTriggerB, sizeof(triggerString), triggerString);
    trigger = pArray->pAttributeList->find(triggerString);
    if (trigger != NULL) {
        status = trigger->getValue(NDAttrFloat64, &triggerValue);
        if (status == asynSuccess) {
            triggerCalcArgs_[1] = triggerValue;
        }
    }
    
    setDoubleParam(NDCircBuffTriggerAVal, triggerCalcArgs_[0]);
    setDoubleParam(NDCircBuffTriggerBVal, triggerCalcArgs_[1]);
    status = calcPerform(triggerCalcArgs_, &calcResult, triggerCalcPostfix_);
    if (status) {
        asynPrint(pasynUserSelf, ASYN_TRACE_ERROR,
            "%s::%s error evaluating expression=%s\n",
            driverName, functionName, calcErrorStr(status));
        return asynError;
    }
    
    if (!isnan(calcResult) && !isinf(calcResult) && (calcResult != 0)) *trig = 1;
    setDoubleParam(NDCircBuffTriggerCalcVal, calcResult);

    return asynSuccess;
}
开发者ID:jlmuir,项目名称:ADCore,代码行数:56,代码来源:NDPluginCircularBuff.cpp

示例2: epicsMutexLock

/** Updates all attribute values in the list; calls NDAttribute::updateValue() for each attribute in the list.
  */
int NDAttributeList::updateValues()
{
  NDAttribute *pAttribute;
  NDAttributeListNode *pListNode;
  //const char *functionName = "NDAttributeList::updateValues";

  epicsMutexLock(this->lock);
  pListNode = (NDAttributeListNode *)ellFirst(&this->list);
  while (pListNode) {
    pAttribute = pListNode->pNDAttribute;
    pAttribute->updateValue();
    pListNode = (NDAttributeListNode *)ellNext(&pListNode->node);
  }
  epicsMutexUnlock(this->lock);
  return(ND_SUCCESS);
}
开发者ID:NSLS-II-CSX,项目名称:xf23id1-ioc1,代码行数:18,代码来源:NDArray.cpp

示例3: attrFileNameSet

/** Look up filename related attributes in the NDArray.
 *  If file name or number is found in the NDArray, the values are replacing the existing ones
 *  in the parameter library. If not found the existing settings remain.
 */
asynStatus NDPluginFile::attrFileNameSet()
{
    asynStatus status = asynSuccess;
    NDAttribute *ndAttr;
    char attrFileName[MAX_FILENAME_LEN];
    epicsInt32 attrFileNumber;
    size_t attrFileNameLen;
    NDAttrDataType_t attrDataType;
    NDArray *pArray = this->pArrays[0];

    if (this->useAttrFilePrefix == false)
        return status;

    /* first check if the attribute contain a fileprefix to form part of the filename. */
    ndAttr = pArray->pAttributeList->find(FILEPLUGIN_NAME);
    if (ndAttr != NULL)
    {
        ndAttr->getValueInfo(&attrDataType, &attrFileNameLen);
        if (attrDataType == NDAttrString)
        {
            if (attrFileNameLen > MAX_FILENAME_LEN) attrFileNameLen = MAX_FILENAME_LEN;
            ndAttr->getValue(NDAttrString, attrFileName, attrFileNameLen);
            setStringParam(NDFileName, attrFileName);
        }
    }

    ndAttr = pArray->pAttributeList->find(FILEPLUGIN_NUMBER);
    if (ndAttr != NULL)
    {
        ndAttr->getValueInfo(&attrDataType, &attrFileNameLen);
        if (attrDataType == NDAttrInt32)
        {
            ndAttr->getValue(NDAttrInt32, &attrFileNumber, 0);
            setIntegerParam(NDFileNumber, attrFileNumber);
            // ensure auto increment is switched off when using attribute file numbers
            setIntegerParam(NDAutoIncrement, 0);
        }
    }
    return status;
}
开发者ID:prjemian,项目名称:ADCore,代码行数:44,代码来源:NDPluginFile.cpp

示例4: attrIsProcessingRequired

/** Decide whether or not this frame is intended to be processed by this plugin.
 * By default all frames are processed. The decision not to process a frame is
 * made based on the string value of the FILEPLUGIN_DESTINATION: if the value does not equal
 * either "all" or the ASYN port name of the current plugin the frame is not to be processed.
 * \param[in] pAttrList  A pointer to the current NDArray's attribute list.
 * \returns true if the frame is to be processed. false if the frame is not to be processed.
 */
bool NDPluginFile::attrIsProcessingRequired(NDAttributeList* pAttrList)
{
    char destPortName[MAX_FILENAME_LEN];
    NDAttribute *ndAttr;
    size_t destPortNameLen;
    NDAttrDataType_t attrDataType;

    ndAttr = pAttrList->find(FILEPLUGIN_DESTINATION);
    if (ndAttr != NULL)
    {
        ndAttr->getValueInfo(&attrDataType, &destPortNameLen);
        if (attrDataType == NDAttrString && destPortNameLen > 1)
        {
            if (destPortNameLen > MAX_FILENAME_LEN)
                destPortNameLen = MAX_FILENAME_LEN;
                ndAttr->getValue(NDAttrString, destPortName, destPortNameLen);
            if (epicsStrnCaseCmp(destPortName, "all", destPortNameLen>3?3:destPortNameLen) != 0 &&
                epicsStrnCaseCmp(destPortName, this->portName, destPortNameLen) != 0)
                return false;
        }
    }
    return true;
}
开发者ID:prjemian,项目名称:ADCore,代码行数:30,代码来源:NDPluginFile.cpp

示例5: attrFileCloseCheck

/** Check whether an attribute asking the file to be closed has been set.
 *  if the value of FILEPLUGIN_CLOSE attribute is set to 1 then close the file.
 */
asynStatus NDPluginFile::attrFileCloseCheck()
{
    asynStatus status = asynSuccess;
    NDAttribute *NDattrFileClose;
    int getStatus = 0;
    int closeFile = 0;
    NDattrFileClose = this->pArrays[0]->pAttributeList->find(FILEPLUGIN_CLOSE);
    // Check for the existence of the parameter
    if (NDattrFileClose != NULL) {
        // Check NDAttribute value (0 = continue, anything else = close file)
        getStatus = NDattrFileClose->getValue(NDAttrInt32, &closeFile);
        if (getStatus == 0){
            if (closeFile != 0){
                // Force a file close
                this->closeFileBase();
                // We must also set the parameter to notify we have stopped capturing
                setIntegerParam(NDFileCapture, 0);
            }
        } else {
            status = asynError;
        }
    }
    return status;
}
开发者ID:prjemian,项目名称:ADCore,代码行数:27,代码来源:NDPluginFile.cpp

示例6: dest

void NTNDArrayConverter::fromAttributes (NDArray *src)
{
    PVStructureArrayPtr dest(m_array->getAttribute());
    NDAttributeList *srcList = src->pAttributeList;
    NDAttribute *attr = NULL;
    StructureConstPtr structure(dest->getStructureArray()->getStructure());
    PVStructureArray::svector destVec(dest->reuse());

    destVec.resize(srcList->count());

    size_t i = 0;
    while((attr = srcList->next(attr)))
    {
        if(!destVec[i].get() || !destVec[i].unique())
            destVec[i] = PVDC->createPVStructure(structure);

        PVStructurePtr pvAttr(destVec[i]);

        pvAttr->getSubField<PVString>("name")->put(attr->getName());
        pvAttr->getSubField<PVString>("descriptor")->put(attr->getDescription());
        pvAttr->getSubField<PVString>("source")->put(attr->getSource());

        NDAttrSource_t sourceType;
        attr->getSourceInfo(&sourceType);
        pvAttr->getSubField<PVInt>("sourceType")->put(sourceType);

        switch(attr->getDataType())
        {
        case NDAttrInt8:      fromAttribute <PVByte,   int8_t>  (pvAttr, attr); break;
        case NDAttrUInt8:     fromAttribute <PVUByte,  uint8_t> (pvAttr, attr); break;
        case NDAttrInt16:     fromAttribute <PVShort,  int16_t> (pvAttr, attr); break;
        case NDAttrUInt16:    fromAttribute <PVUShort, uint16_t>(pvAttr, attr); break;
        case NDAttrInt32:     fromAttribute <PVInt,    int32_t> (pvAttr, attr); break;
        case NDAttrUInt32:    fromAttribute <PVUInt,   uint32_t>(pvAttr, attr); break;
        case NDAttrFloat32:   fromAttribute <PVFloat,  float>   (pvAttr, attr); break;
        case NDAttrFloat64:   fromAttribute <PVDouble, double>  (pvAttr, attr); break;
        case NDAttrString:    fromStringAttribute(pvAttr, attr); break;
        case NDAttrUndefined: fromUndefinedAttribute(pvAttr); break;
        default:              throw std::runtime_error("invalid attribute data type");
        }

        ++i;
    }

    dest->replace(freeze(destVec));
}
开发者ID:ajgdls,项目名称:ADCore,代码行数:46,代码来源:ntndArrayConverter.cpp

示例7: writeFileBase

/** Base method for writing a file
  * Handles logic for NDFileModeSingle, NDFileModeCapture and NDFileModeStream when the derived class does or
  * does not support NDPulginFileMultiple. Calls writeFile in the derived class. */
asynStatus NDPluginFile::writeFileBase() 
{
    int status = asynSuccess;
    int fileWriteMode;
    int numCapture, numCaptured;
    int i;
    int deleteDriverFile;
    NDArray *pArray;
    NDAttribute *pAttribute;
    char driverFileName[MAX_FILENAME_LEN];
    char errorMessage[256];
    const char* functionName = "writeFileBase";

    /* Make sure there is a valid array */
    if (!this->pArrays[0]) {
        asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR,
            "%s:%s: ERROR, must collect an array to get dimensions first\n",
            driverName, functionName);
        return(asynError);
    }
    
    getIntegerParam(NDFileWriteMode, &fileWriteMode);    
    getIntegerParam(NDFileNumCapture, &numCapture);    
    getIntegerParam(NDFileNumCaptured, &numCaptured);

    setIntegerParam(NDFileWriteStatus, NDFileWriteOK);
    setStringParam(NDFileWriteMessage, "");
    
    /* We unlock the overall mutex here because we want the callbacks to be able to queue new
     * frames without waiting while we write files here.  The only restriction is that the
     * callbacks must not modify any part of the class structure that we use here. */

    switch(fileWriteMode) {
        case NDFileModeSingle:
            setIntegerParam(NDWriteFile, 1);
            callParamCallbacks();
            status = this->openFileBase(NDFileModeWrite, this->pArrays[0]);
            if (status == asynSuccess) {
                this->unlock();
                epicsMutexLock(this->fileMutexId);
                status = this->writeFile(this->pArrays[0]);
                epicsMutexUnlock(this->fileMutexId);
                this->lock();
                if (status) {
                    epicsSnprintf(errorMessage, sizeof(errorMessage)-1, 
                        "Error writing file, status=%d", status);
                    asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
                          "%s:%s %s\n", 
                          driverName, functionName, errorMessage);
                    setIntegerParam(NDFileWriteStatus, NDFileWriteError);
                    setStringParam(NDFileWriteMessage, errorMessage);
                } else {
                    status = this->closeFileBase(); 
                }
            }
            setIntegerParam(NDWriteFile, 0);
            callParamCallbacks();
            break;
        case NDFileModeCapture:
            /* Write the file */
            if (!this->pCapture) {
                asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR,
                    "%s:%s: ERROR, no capture buffer present\n", 
                    driverName, functionName);
                setIntegerParam(NDFileWriteStatus, NDFileWriteError);
                setStringParam(NDFileWriteMessage, "ERROR, no capture buffer present");
                break;
            }
            setIntegerParam(NDWriteFile, 1);
            callParamCallbacks();
            if (this->supportsMultipleArrays)
                status = this->openFileBase(NDFileModeWrite | NDFileModeMultiple, this->pArrays[0]);
            if (status == asynSuccess) {
                for (i=0; i<numCaptured; i++) {
                    pArray = this->pCapture[i];
                    if (!this->supportsMultipleArrays)
                        status = this->openFileBase(NDFileModeWrite, pArray);
                    if (status == asynSuccess) {
                        this->unlock();
                        epicsMutexLock(this->fileMutexId);
                        status = this->writeFile(pArray);
                        epicsMutexUnlock(this->fileMutexId);
                        this->lock();
                        if (status) {
                            epicsSnprintf(errorMessage, sizeof(errorMessage)-1, 
                                "Error writing file, status=%d", status);
                            asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
                                  "%s:%s %s\n", 
                                  driverName, functionName, errorMessage);
                            setIntegerParam(NDFileWriteStatus, NDFileWriteError);
                            setStringParam(NDFileWriteMessage, errorMessage);
                        } else {
                            if (!this->supportsMultipleArrays)
                                status = this->closeFileBase();
                        }
                    }
                }
//.........这里部分代码省略.........
开发者ID:NSLS-II-CSX,项目名称:xf23id1-ioc1,代码行数:101,代码来源:NDPluginFile.cpp

示例8: getInfo

/** Convenience method returns information about an NDArray, including the total number of elements, 
  * the number of bytes per element, and the total number of bytes in the array.
  \param[out] pInfo Pointer to an NDArrayInfo_t structure, must have been allocated by caller. */
int NDArray::getInfo(NDArrayInfo_t *pInfo)
{
  int i;
  NDAttribute *pAttribute;

  switch(this->dataType) {
    case NDInt8:
      pInfo->bytesPerElement = sizeof(epicsInt8);
      break;
    case NDUInt8:
      pInfo->bytesPerElement = sizeof(epicsUInt8);
      break;
    case NDInt16:
      pInfo->bytesPerElement = sizeof(epicsInt16);
      break;
    case NDUInt16:
      pInfo->bytesPerElement = sizeof(epicsUInt16);
      break;
    case NDInt32:
      pInfo->bytesPerElement = sizeof(epicsInt32);
      break;
    case NDUInt32:
      pInfo->bytesPerElement = sizeof(epicsUInt32);
      break;
    case NDFloat32:
      pInfo->bytesPerElement = sizeof(epicsFloat32);
      break;
    case NDFloat64:
      pInfo->bytesPerElement = sizeof(epicsFloat64);
      break;
    default:
      return(ND_ERROR);
      break;
  }
  pInfo->nElements = 1;
  for (i=0; i<this->ndims; i++) pInfo->nElements *= this->dims[i].size;
  pInfo->totalBytes = pInfo->nElements * pInfo->bytesPerElement;
  pInfo->colorMode = NDColorModeMono;
  pAttribute = this->pAttributeList->find("ColorMode");
  if (pAttribute) pAttribute->getValue(NDAttrInt32, &pInfo->colorMode);
  pInfo->xDim        = 0;
  pInfo->yDim        = 0;
  pInfo->colorDim    = 0;
  pInfo->xSize       = 0;
  pInfo->ySize       = 0;
  pInfo->colorSize   = 0;
  pInfo->xStride     = 0;
  pInfo->yStride     = 0;
  pInfo->colorStride = 0;
  if (this->ndims > 0) {
    pInfo->xStride = 1;
    pInfo->xSize   = this->dims[0].size;
  }
  if (this->ndims > 1) {
    pInfo->yDim  = 1;
    pInfo->yStride = pInfo->xSize;
    pInfo->ySize   = this->dims[1].size;
  }
  if (this->ndims == 3) {
    switch (pInfo->colorMode) {
      case NDColorModeRGB1:
        pInfo->xDim    = 1;
        pInfo->yDim    = 2;
        pInfo->colorDim  = 0;
        pInfo->xStride   = this->dims[0].size;
        pInfo->yStride   = this->dims[0].size * this->dims[1].size;
        pInfo->colorStride = 1;
        break;
      case NDColorModeRGB2:
        pInfo->xDim    = 0;
        pInfo->yDim    = 2;
        pInfo->colorDim  = 1;
        pInfo->xStride   = 1;
        pInfo->yStride   = this->dims[0].size * this->dims[1].size;
        pInfo->colorStride = this->dims[0].size;
        break;
      case NDColorModeRGB3:
        pInfo->xDim    = 0;
        pInfo->yDim    = 1;
        pInfo->colorDim  = 2;
        pInfo->xStride   = 1;
        pInfo->yStride   = this->dims[0].size;
        pInfo->colorStride = this->dims[0].size * this->dims[1].size;
        break;
      default:
        break;
    }
    pInfo->xSize     = this->dims[pInfo->xDim].size;
    pInfo->ySize     = this->dims[pInfo->yDim].size;
    pInfo->colorSize = this->dims[pInfo->colorDim].size;
  }
  return(ND_SUCCESS);
}
开发者ID:NSLS-II-CSX,项目名称:xf23id1-ioc1,代码行数:96,代码来源:NDArray.cpp

示例9: if

void* epics2hdf::getNDAttr(const char* attr_name, void* attr_val,
      hid_t *datatype)
{
   NDAttrDataType_t attrDataType;
   NDAttribute *pAttr;
   size_t attrDataSize;
   hid_t nd_hdf_type;

   if (strcmp(attr_name, "sysclock") == 0)
   {
      *datatype = H5T_NATIVE_DOUBLE;
      double *x;
      x = (double*) attr_val;
      *x = clock() / CLOCKS_PER_SEC;
   }
   else if (strcmp(attr_name, "timestamp") == 0)
   {
      *datatype = H5T_NATIVE_DOUBLE;
      double *x;
      x = (double*) attr_val;
      *x = pArray->timeStamp;
   }
   else if (strcmp(attr_name, "uniqueId") == 0)
   {
      *datatype = H5T_NATIVE_INT;
      int *x;
      x = (int*) attr_val;
      *x = pArray->uniqueId;
   }
   else if (strcmp(attr_name, "datetime") == 0)
   {
      //2003-04-01T13:01:02 is ISO format.
      time_t rawtime;

      struct tm *today;
      char tstr[128];
      time(&rawtime);
      today = localtime(&rawtime);
      sprintf(tstr, "%04i-%02i-%02iT%02i:%02i:%02i", today->tm_year + 1900,
            today->tm_mon + 1, today->tm_mday, today->tm_hour, today->tm_min,
            today->tm_sec);

      *datatype = H5T_STR_NULLTERM;
      strcpy((char*) attr_val, tstr);

   }
   else
   {
      pAttr = pArray->pAttributeList->find(attr_name);

      if (pAttr != NULL)
      {
         pAttr->getValueInfo(&attrDataType, &attrDataSize);
         nd_hdf_type = type_ndatr2hdf(attrDataType);

         *datatype = nd_hdf_type;

         if (nd_hdf_type >= 0)
         {

            pAttr->getValue(attrDataType, (char *) attr_val, attrDataSize);
         }
         else
         {
            printf("epics2hdf::getNDAttr bad NDAttr datatype %s\n", attr_name);
            *datatype = 0;
            strcpy((char*) attr_val, "Error: Unknown Attribute Datatype");

         }
      } //pAttr
      else
      {
         int attrCount;
         printf("epics2hdf::getNDAttr Could not find NDAttr %s\n", attr_name);
         *datatype = 0;
         strcpy((char*) attr_val, "Error: Unknown Attribute");
         // list the attributes
         printf("List of attributes in image\n");
         pAttr = pArray->pAttributeList->next(NULL);
         for (attrCount = 0; attrCount < pArray->pAttributeList->count();
               attrCount++)
         {

            printf("Attr: %s \n", pAttr->pName);
            pAttr = pArray->pAttributeList->next(pAttr);
         }

      } //pAttr
   }

   return (attr_val);
}
开发者ID:Engbretson,项目名称:IMM_Plugin,代码行数:92,代码来源:NDFileHDF5XML.cpp

示例10: openFile

/** Opens a TIFF file.
  * \param[in] fileName The name of the file to open.
  * \param[in] openMode Mask defining how the file should be opened; bits are 
  *            NDFileModeRead, NDFileModeWrite, NDFileModeAppend, NDFileModeMultiple
  * \param[in] pArray A pointer to an NDArray; this is used to determine the array and attribute properties.
  */
asynStatus NDFileTIFF::openFile(const char *fileName, NDFileOpenMode_t openMode, NDArray *pArray)
{
    /* When we create TIFF variables and dimensions, we get back an
     * ID for each one. */
    static const char *functionName = "openFile";
    size_t sizeX, sizeY, rowsPerStrip;
    int bitsPerSample=8, sampleFormat=SAMPLEFORMAT_INT, samplesPerPixel, photoMetric, planarConfig;
    int colorMode=NDColorModeMono;
    NDAttribute *pAttribute;
    char ManufacturerString[MAX_ATTRIBUTE_STRING_SIZE] = "Unknown";
    char ModelString[MAX_ATTRIBUTE_STRING_SIZE] = "Unknown";

    /* We don't support reading yet */
    if (openMode & NDFileModeRead) return(asynError);

    /* We don't support opening an existing file for appending yet */
    if (openMode & NDFileModeAppend) return(asynError);

   /* Create the file. */
    if ((this->output = TIFFOpen(fileName, "w")) == NULL ) {
        asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
        "%s:%s error opening file %s\n",
        driverName, functionName, fileName);
        return(asynError);
    }
    /* We do some special treatment based on colorMode */
    pAttribute = pArray->pAttributeList->find("ColorMode");
    if (pAttribute) pAttribute->getValue(NDAttrInt32, &colorMode);

    switch (pArray->dataType) {
        case NDInt8:
            sampleFormat = SAMPLEFORMAT_INT;
            bitsPerSample = 8;
            break;
        case NDUInt8:
            sampleFormat = SAMPLEFORMAT_UINT;
            bitsPerSample = 8;
            break;
        case NDInt16:
            sampleFormat = SAMPLEFORMAT_INT;
            bitsPerSample = 16;
            break;
        case NDUInt16:
            sampleFormat = SAMPLEFORMAT_UINT;
            bitsPerSample = 16;
            break;
        case NDInt32:
            sampleFormat = SAMPLEFORMAT_INT;
            bitsPerSample = 32;
            break;
        case NDUInt32:
            sampleFormat = SAMPLEFORMAT_UINT;
            bitsPerSample = 32;
            break;
        case NDFloat32:
            sampleFormat = SAMPLEFORMAT_IEEEFP;
            bitsPerSample = 32;
            break;
        case NDFloat64:
            sampleFormat = SAMPLEFORMAT_IEEEFP;
            bitsPerSample = 64;
            break;
    }
    if (pArray->ndims == 2) {
        sizeX = pArray->dims[0].size;
        sizeY = pArray->dims[1].size;
        rowsPerStrip = sizeY;
        samplesPerPixel = 1;
        photoMetric = PHOTOMETRIC_MINISBLACK;
        planarConfig = PLANARCONFIG_CONTIG;
        this->colorMode = NDColorModeMono;
    } else if ((pArray->ndims == 3) && (pArray->dims[0].size == 3) && (colorMode == NDColorModeRGB1)) {
        sizeX = pArray->dims[1].size;
        sizeY = pArray->dims[2].size;
        rowsPerStrip = sizeY;
        samplesPerPixel = 3;
        photoMetric = PHOTOMETRIC_RGB;
        planarConfig = PLANARCONFIG_CONTIG;
        this->colorMode = NDColorModeRGB1;
    } else if ((pArray->ndims == 3) && (pArray->dims[1].size == 3) && (colorMode == NDColorModeRGB2)) {
        sizeX = pArray->dims[0].size;
        sizeY = pArray->dims[2].size;
        rowsPerStrip = 1;
        samplesPerPixel = 3;
        photoMetric = PHOTOMETRIC_RGB;
        planarConfig = PLANARCONFIG_SEPARATE;
        this->colorMode = NDColorModeRGB2;
    } else if ((pArray->ndims == 3) && (pArray->dims[2].size == 3) && (colorMode == NDColorModeRGB3)) {
        sizeX = pArray->dims[0].size;
        sizeY = pArray->dims[1].size;
        rowsPerStrip = sizeY;
        samplesPerPixel = 3;
        photoMetric = PHOTOMETRIC_RGB;
        planarConfig = PLANARCONFIG_SEPARATE;
//.........这里部分代码省略.........
开发者ID:NSLS-II-CSX,项目名称:xf23id1-ioc1,代码行数:101,代码来源:NDFileTIFF.cpp

示例11: processNode

int NDFileNexus::processNode(TiXmlNode *curNode, NDArray *pArray) {
  int status = 0;
  const char *nodeName;
  const char *nodeValue;
  const char *nodeOuttype;
  const char *nodeSource;
  const char *nodeType;
  //float data;
  int rank;
  NDDataType_t type;
  int ii;
  int dims[ND_ARRAY_MAX_DIMS];
  int numCapture;
  int fileWriteMode;
  NDAttrDataType_t attrDataType;
  NDAttribute *pAttr;
  size_t attrDataSize;
  size_t nodeTextLen;
  int wordSize;
  int dataOutType=NDInt8;
  size_t numWords;
  int numItems = 0;
  int addr =0;
  void *pValue;
  char nodeText[256];
  NXname dataclass;
  NXname dPath;
  static const char *functionName = "processNode";

  asynPrint(this->pasynUserSelf, ASYN_TRACE_FLOW,
            "Entering %s:%s\n", driverName, functionName );

  /* Must lock when accessing parameter library */
  this->lock();
  getIntegerParam(addr, NDFileWriteMode, &fileWriteMode);
  getIntegerParam(addr, NDFileNumCapture, &numCapture);
  this->unlock();

  nodeValue = curNode->Value();
  asynPrint(this->pasynUserSelf, ASYN_TRACEIO_DRIVER,
            "%s:%s  Value=%s Type=%d\n", driverName, functionName,
            curNode->Value(), curNode->Type());
  nodeType = curNode->ToElement()->Attribute("type");
  NXstatus stat;
  if (strcmp (nodeValue, "NXroot") == 0) {
    this->iterateNodes(curNode, pArray);
  }  /*  only include all the NeXus base classes */
  else if ((strcmp (nodeValue, "NXentry") ==0) ||
           (strcmp (nodeValue, "NXinstrument") ==0) ||
           (strcmp (nodeValue, "NXsample") ==0) ||
           (strcmp (nodeValue, "NXmonitor") ==0) ||
           (strcmp (nodeValue, "NXsource") ==0) ||
           (strcmp (nodeValue, "NXuser") ==0) ||
           (strcmp (nodeValue, "NXdata") ==0) ||
           (strcmp (nodeValue, "NXdetector") ==0) ||
           (strcmp (nodeValue, "NXaperature") ==0) ||
           (strcmp (nodeValue, "NXattenuator") ==0) ||
           (strcmp (nodeValue, "NXbeam_stop") ==0) ||
           (strcmp (nodeValue, "NXbending_magnet") ==0) ||
           (strcmp (nodeValue, "NXcollimator") ==0) ||
           (strcmp (nodeValue, "NXcrystal") ==0) ||
           (strcmp (nodeValue, "NXdisk_chopper") ==0) ||
           (strcmp (nodeValue, "NXfermi_chopper") ==0) ||
           (strcmp (nodeValue, "NXfilter") ==0) ||
           (strcmp (nodeValue, "NXflipper") ==0) ||
           (strcmp (nodeValue, "NXguide") ==0) ||
           (strcmp (nodeValue, "NXinsertion_device") ==0) ||
           (strcmp (nodeValue, "NXmirror") ==0) ||
           (strcmp (nodeValue, "NXmoderator") ==0) ||
           (strcmp (nodeValue, "NXmonochromator") ==0) ||
           (strcmp (nodeValue, "NXpolarizer") ==0) ||
           (strcmp (nodeValue, "NXpositioner") ==0) ||
           (strcmp (nodeValue, "NXvelocity_selector") ==0) ||
           (strcmp (nodeValue, "NXevent_data") ==0) ||
           (strcmp (nodeValue, "NXprocess") ==0) ||
           (strcmp (nodeValue, "NXcharacterization") ==0) ||
           (strcmp (nodeValue, "NXlog") ==0) ||
           (strcmp (nodeValue, "NXnote") ==0) ||
           (strcmp (nodeValue, "NXbeam") ==0) ||
           (strcmp (nodeValue, "NXgeometry") ==0) ||
           (strcmp (nodeValue, "NXtranslation") ==0) ||
           (strcmp (nodeValue, "NXshape") ==0) ||
           (strcmp (nodeValue, "NXorientation") ==0) ||
           (strcmp (nodeValue, "NXenvironment") ==0) ||
           (strcmp (nodeValue, "NXsensor") ==0) ||
           (strcmp (nodeValue, "NXcapillary") ==0) ||
           (strcmp (nodeValue, "NXcollection") ==0) ||
           (strcmp (nodeValue, "NXdetector_group") ==0) ||
           (strcmp (nodeValue, "NXparameters") ==0) ||
           (strcmp (nodeValue, "NXsubentry") ==0) ||
           (strcmp (nodeValue, "NXxraylens") ==0) ||
           (nodeType && strcmp (nodeType, "UserGroup") == 0) ) {
  nodeName = curNode->ToElement()->Attribute("name");
  if (nodeName == NULL) {
    nodeName = nodeValue;
  }
  stat = NXmakegroup(this->nxFileHandle, (const char *)nodeName, (const char *)nodeValue);
  stat |= NXopengroup(this->nxFileHandle, (const char *)nodeName, (const char *)nodeValue);
  if (stat != NX_OK ) {
    asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR,
//.........这里部分代码省略.........
开发者ID:dhickin,项目名称:ADCore,代码行数:101,代码来源:NDFileNexus.cpp

示例12: writeFileBase

/** Base method for writing a file
  * Handles logic for NDFileModeSingle, NDFileModeCapture and NDFileModeStream when the derived class does or
  * does not support NDPulginFileMultiple. Calls writeFile in the derived class. */
asynStatus NDPluginFile::writeFileBase() 
{
    int status = asynSuccess;
    int fileWriteMode;
    int numCapture, numCaptured;
    int i;
    bool doLazyOpen;
    int deleteDriverFile;
    NDArray *pArray;
    NDAttribute *pAttribute;
    char driverFileName[MAX_FILENAME_LEN];
    char errorMessage[256];
    static const char* functionName = "writeFileBase";

    /* Make sure there is a valid array */
    if (!this->pArrays[0]) {
        asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR,
            "%s::%s: ERROR, must collect an array to get dimensions first\n",
            driverName, functionName);
        return(asynError);
    }
    
    NDArray *pArrayOut = this->pArrays[0];
    // Must increase reference count on this array because another thread might decrement the count on pArrays[0]
    // when we have the mutex unlocked
    pArrayOut->reserve();

    getIntegerParam(NDFileWriteMode, &fileWriteMode);    
    getIntegerParam(NDFileNumCapture, &numCapture);    
    getIntegerParam(NDFileNumCaptured, &numCaptured);

    setIntegerParam(NDFileWriteStatus, NDFileWriteOK);
    setStringParam(NDFileWriteMessage, "");
    
    /* We unlock the overall mutex here because we want the callbacks to be able to queue new
     * frames without waiting while we write files here.  The only restriction is that the
     * callbacks must not modify any part of the class structure that we use here. */

    switch(fileWriteMode) {
        case NDFileModeSingle:
            setIntegerParam(NDWriteFile, 1);
            callParamCallbacks();
            // Some file writing plugins (e.g. HDF5) use the value of NDFileNumCaptured 
            // even in single mode
            setIntegerParam(NDFileNumCaptured, 1);
            status = this->openFileBase(NDFileModeWrite, pArrayOut);
            if (status == asynSuccess) {
                this->unlock();
                epicsMutexLock(this->fileMutexId);
                status = this->writeFile(pArrayOut);
                epicsMutexUnlock(this->fileMutexId);
                this->lock();
                NDPluginDriver::endProcessCallbacks(pArrayOut, true, true);
                if (status) {
                    epicsSnprintf(errorMessage, sizeof(errorMessage)-1, 
                        "Error writing file, status=%d", status);
                    asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
                          "%s::%s %s\n", 
                          driverName, functionName, errorMessage);
                    setIntegerParam(NDFileWriteStatus, NDFileWriteError);
                    setStringParam(NDFileWriteMessage, errorMessage);
                } else {
                    status = this->closeFileBase(); 
                }
            }
            setIntegerParam(NDWriteFile, 0);
            callParamCallbacks();
            break;
        case NDFileModeCapture:
            /* Write the file */
            if (!this->pCapture) {
                asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR,
                    "%s::%s: ERROR, no capture buffer present\n", 
                    driverName, functionName);
                setIntegerParam(NDFileWriteStatus, NDFileWriteError);
                setStringParam(NDFileWriteMessage, "ERROR, no capture buffer present");
                break;
            }
            setIntegerParam(NDWriteFile, 1);
            callParamCallbacks();
            if (this->supportsMultipleArrays)
                status = this->openFileBase(NDFileModeWrite | NDFileModeMultiple, pArrayOut);
            if (status == asynSuccess) {
                for (i=0; i<numCaptured; i++) {
                    pArray = this->pCapture[i];
                    if (!this->supportsMultipleArrays)
                        status = this->openFileBase(NDFileModeWrite, pArray);
                    else
                        this->attrFileNameCheck();
                    if (status == asynSuccess) {
                        this->unlock();
                        epicsMutexLock(this->fileMutexId);
                        status = this->writeFile(pArray);
                        epicsMutexUnlock(this->fileMutexId);
                        this->lock();
                        NDPluginDriver::endProcessCallbacks(pArray, true, true);
                        if (status) {
//.........这里部分代码省略.........
开发者ID:prjemian,项目名称:ADCore,代码行数:101,代码来源:NDPluginFile.cpp

示例13: formatArray

/** Format an NDArray as an AVFrame using the codec context c.
Use inPicture to wrap the data in pArray, use swscale to convert it to scPicture
using the output parameters stored in c. Special case for gray8 -> YUVx, can
use the data as is and add a neutral array for the colour info.
*/
int formatArray(NDArray *pArray, asynUser *pasynUser, AVFrame *inPicture,
		struct SwsContext **pCtx, AVCodecContext *c, AVFrame *scPicture) {
    static const char *functionName = "formatArray";
    int colorMode = NDColorModeMono;
	int width, height;
	PixelFormat pix_fmt;
	NDAttribute *pAttribute = NULL;
	int Int16;
	
	/* only support 8 and 16 bit data for now */
    switch (pArray->dataType) {
        case NDInt8:
        case NDUInt8:
            Int16 = 0;
            break;
        case NDInt16:
        case NDUInt16:       
            Int16 = 1; 
            break;
        default:
            asynPrint(pasynUser, ASYN_TRACE_ERROR, 
                "%s: only 8 or 16-bit data is supported\n", functionName);
        	return(asynError);
    }	

	/* Get the colormode of the array */	
    pAttribute = pArray->pAttributeList->find("ColorMode");
    if (pAttribute) pAttribute->getValue(NDAttrInt32, &colorMode);

    /* We do some special treatment based on colorMode */
    if ((pArray->ndims == 2) && (colorMode == NDColorModeMono)) {
        width  = (int) pArray->dims[0].size;
        height = (int) pArray->dims[1].size;
        if (Int16) {
            pix_fmt = PIX_FMT_GRAY16;
        } else if (width != c->width || height != c->height) {
        	pix_fmt = PIX_FMT_GRAY8;
        } else {
        	int stride;
            pix_fmt = PIX_FMT_GRAY8;
            /* special case for gray8, and planar outputs, don't need to scale, 
               can use a neutral array */
            switch (c->pix_fmt) {
    			case PIX_FMT_YUV420P:   //< planar YUV 4:2:0, 12bpp, (1 Cr & Cb sample per 2x2 Y samples)
    			case PIX_FMT_YUV411P:   //< planar YUV 4:1:1, 12bpp, (1 Cr & Cb sample per 4x1 Y samples)
    			case PIX_FMT_YUVJ420P:  //< planar YUV 4:2:0, 12bpp, full scale (JPEG), deprecated in favor of PIX_FMT_YUV420P and setting color_range
    			case PIX_FMT_NV12:      //< planar YUV 4:2:0, 12bpp, 1 plane for Y and 1 plane for the UV components, which are interleaved (first byte U and the following byte V)
    			case PIX_FMT_NV21:      //< as above, but U and V bytes are swapped
    				stride = 4;
    				break;
    			case PIX_FMT_YUV422P:   //< planar YUV 4:2:2, 16bpp, (1 Cr & Cb sample per 2x1 Y samples)
    			case PIX_FMT_YUVJ422P:  //< planar YUV 4:2:2, 16bpp, full scale (JPEG), deprecated in favor of PIX_FMT_YUV422P and setting color_range
    			case PIX_FMT_YUV440P:   //< planar YUV 4:4:0 (1 Cr & Cb sample per 1x2 Y samples)
    			case PIX_FMT_YUVJ440P:  //< planar YUV 4:4:0 full scale (JPEG), deprecated in favor of PIX_FMT_YUV440P and setting color_range    			
    				stride = 2;
    				break;    				
    			case PIX_FMT_YUV444P:   //< planar YUV 4:4:4, 24bpp, (1 Cr & Cb sample per 1x1 Y samples)    			
    			case PIX_FMT_YUVJ444P:  //< planar YUV 4:4:4, 24bpp, full scale (JPEG), deprecated in favor of PIX_FMT_YUV444P and setting color_range
					stride = 1;
    				break;	
    			default:
    				stride = 0;
    				break;				
			}			
			if (stride) {	
	    	    scPicture->data[0] = (uint8_t*) pArray->pData;
    		    scPicture->data[1] = (uint8_t*) neutral;
    		    scPicture->data[2] = (uint8_t*) neutral;    	        	    
		        scPicture->linesize[0] = width;
		        scPicture->linesize[1] = width / stride;
		        scPicture->linesize[2] = width / stride;
				return(asynSuccess);		        
		    }
		}
        /* setup the input picture */
        inPicture->data[0] = (uint8_t*) pArray->pData;
        inPicture->linesize[0] = width * (Int16 + 1);
    } else if ((pArray->ndims == 3) && (pArray->dims[0].size == 3) && (colorMode == NDColorModeRGB1)) {
        width  = (int) pArray->dims[1].size;
        height = (int) pArray->dims[2].size;
        if (Int16) {
            pix_fmt = PIX_FMT_RGB48;
        } else {
            pix_fmt = PIX_FMT_RGB24;
        }    
        /* setup the input picture */
        inPicture->data[0] = (uint8_t*) pArray->pData;
        inPicture->linesize[0] = width * (Int16 + 1) * 3;          
    } else {
        asynPrint(pasynUser, ASYN_TRACE_ERROR, 
            "%s: unsupported array structure\n", functionName);
        return(asynError);
    }

	/* setup the swscale ctx */   
//.........这里部分代码省略.........
开发者ID:ISISComputingGroup,项目名称:EPICS-areaDetector,代码行数:101,代码来源:ffmpegCommon.cpp

示例14: openFile

/** Opens a JPEG file.
  * \param[in] fileName The name of the file to open.
  * \param[in] openMode Mask defining how the file should be opened; bits are 
  *            NDFileModeRead, NDFileModeWrite, NDFileModeAppend, NDFileModeMultiple
  * \param[in] pArray A pointer to an NDArray; this is used to determine the array and attribute properties.
  */
asynStatus NDFileJPEG::openFile(const char *fileName, NDFileOpenMode_t openMode, NDArray *pArray)
{
    static const char *functionName = "openFile";
    int colorMode = NDColorModeMono;
    NDAttribute *pAttribute;
    int quality;

    /* We don't support reading yet */
    if (openMode & NDFileModeRead) return(asynError);

    /* We don't support opening an existing file for appending yet */
    if (openMode & NDFileModeAppend) return(asynError);

    switch (pArray->dataType) {
        case NDInt8:
        case NDUInt8:
            break;
        default:
            asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
            "%s:%s: only 8-bit data is supported\n",
            driverName, functionName);
        return(asynError);

    }

    /* We do some special treatment based on colorMode */
    pAttribute = pArray->pAttributeList->find("ColorMode");
    if (pAttribute) pAttribute->getValue(NDAttrInt32, &colorMode);

    if (pArray->ndims == 2) {
        this->jpegInfo.image_width  = (JDIMENSION)pArray->dims[0].size;
        this->jpegInfo.image_height = (JDIMENSION)pArray->dims[1].size;
        this->jpegInfo.input_components = 1;
        this->jpegInfo.in_color_space = JCS_GRAYSCALE;
        this->colorMode = NDColorModeMono;
    } else if ((pArray->ndims == 3) && (pArray->dims[0].size == 3) && (colorMode == NDColorModeRGB1)) {
        this->jpegInfo.image_width  = (JDIMENSION)pArray->dims[1].size;
        this->jpegInfo.image_height = (JDIMENSION)pArray->dims[2].size;
        this->jpegInfo.input_components = 3;
        this->jpegInfo.in_color_space = JCS_RGB;
        this->colorMode = NDColorModeRGB1;
    } else if ((pArray->ndims == 3) && (pArray->dims[1].size == 3) && (colorMode == NDColorModeRGB2)) {
        this->jpegInfo.image_width  = (JDIMENSION)pArray->dims[0].size;
        this->jpegInfo.image_height = (JDIMENSION)pArray->dims[2].size;
        this->jpegInfo.input_components = 3;
        this->jpegInfo.in_color_space = JCS_RGB;
        this->colorMode = NDColorModeRGB2;
    } else if ((pArray->ndims == 3) && (pArray->dims[2].size == 3) && (colorMode == NDColorModeRGB3)) {
        this->jpegInfo.image_width  = (JDIMENSION)pArray->dims[0].size;
        this->jpegInfo.image_height = (JDIMENSION)pArray->dims[1].size;
        this->jpegInfo.input_components = 3;
        this->jpegInfo.in_color_space = JCS_RGB;
        this->colorMode = NDColorModeRGB3;
    } else {
        asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
            "%s:%s: unsupported array structure\n",
            driverName, functionName);
        return(asynError);
    }

   /* Create the file. */
    if ((this->outFile = fopen(fileName, "wb")) == NULL ) {
        asynPrint(this->pasynUserSelf, ASYN_TRACE_ERROR, 
        "%s:%s error opening file %s\n",
        driverName, functionName, fileName);
        return(asynError);
    }
    
    jpeg_set_defaults(&this->jpegInfo);

    /* Set the file quality */
    /* Must lock when accessing parameter library */
    this->lock();
    getIntegerParam(NDFileJPEGQuality, &quality);
    this->unlock();
    jpeg_set_quality(&this->jpegInfo, quality, TRUE);
    
    jpeg_start_compress(&this->jpegInfo, TRUE);
    return(asynSuccess);
}
开发者ID:argonnexraydetector,项目名称:ADCore,代码行数:86,代码来源:NDFileJPEG.cpp

示例15: convert

/** Creates a new output NDArray from an input NDArray, performing
  * conversion operations.
  * The conversion can change the data type if dataTypeOut is different from
  * pIn->dataType. It can also change the dimensions. outDims may have different
  * values of size, binning, offset and reverse for each of its dimensions from input
  * array dimensions (pIn->dims).
  * \param[in] pIn The input array, source of the conversion.
  * \param[out] ppOut The output array, result of the conversion.
  * \param[in] dataTypeOut The data type of the output array.
  * \param[in] dimsOut The dimensions of the output array.
  */
int NDArrayPool::convert(NDArray *pIn,
                         NDArray **ppOut,
                         NDDataType_t dataTypeOut,
                         NDDimension_t *dimsOut)
{
  int dimsUnchanged;
  size_t dimSizeOut[ND_ARRAY_MAX_DIMS];
  NDDimension_t dimsOutCopy[ND_ARRAY_MAX_DIMS];
  int i;
  NDArray *pOut;
  NDArrayInfo_t arrayInfo;
  NDAttribute *pAttribute;
  int colorMode, colorModeMono = NDColorModeMono;
  const char *functionName = "convert";

  /* Initialize failure */
  *ppOut = NULL;

  /* Copy the input dimension array because we need to modify it
   * but don't want to affect caller */
  memcpy(dimsOutCopy, dimsOut, pIn->ndims*sizeof(NDDimension_t));
  /* Compute the dimensions of the output array */
  dimsUnchanged = 1;
  for (i=0; i<pIn->ndims; i++) {
    dimsOutCopy[i].size = dimsOutCopy[i].size/dimsOutCopy[i].binning;
    if (dimsOutCopy[i].size <= 0) {
      printf("%s:%s: ERROR, invalid output dimension, size=%d, binning=%d\n",
             driverName, functionName, (int)dimsOut[i].size, dimsOut[i].binning);
      return(ND_ERROR);
    }
    dimSizeOut[i] = dimsOutCopy[i].size;
    if ((pIn->dims[i].size  != dimsOutCopy[i].size) ||
      (dimsOutCopy[i].offset != 0) ||
      (dimsOutCopy[i].binning != 1) ||
      (dimsOutCopy[i].reverse != 0)) dimsUnchanged = 0;
  }

  /* We now know the datatype and dimensions of the output array.
   * Allocate it */
  pOut = alloc(pIn->ndims, dimSizeOut, dataTypeOut, 0, NULL);
  *ppOut = pOut;
  if (!pOut) {
    printf("%s:%s: ERROR, cannot allocate output array\n",
           driverName, functionName);
    return(ND_ERROR);
  }
  /* Copy fields from input to output */
  pOut->timeStamp = pIn->timeStamp;
  pOut->epicsTS = pIn->epicsTS;
  pOut->uniqueId = pIn->uniqueId;
  /* Replace the dimensions with those passed to this function */
  memcpy(pOut->dims, dimsOutCopy, pIn->ndims*sizeof(NDDimension_t));
  pIn->pAttributeList->copy(pOut->pAttributeList);

  pOut->getInfo(&arrayInfo);

  if (dimsUnchanged) {
    if (pIn->dataType == pOut->dataType) {
      /* The dimensions are the same and the data type is the same,
       * then just copy the input image to the output image */
      memcpy(pOut->pData, pIn->pData, arrayInfo.totalBytes);
      return ND_SUCCESS;
    } else {
      /* We need to convert data types */
      switch(pOut->dataType) {
        case NDInt8:
          convertTypeSwitch <epicsInt8> (pIn, pOut);
          break;
        case NDUInt8:
          convertTypeSwitch <epicsUInt8> (pIn, pOut);
          break;
        case NDInt16:
          convertTypeSwitch <epicsInt16> (pIn, pOut);
          break;
        case NDUInt16:
          convertTypeSwitch <epicsUInt16> (pIn, pOut);
          break;
        case NDInt32:
          convertTypeSwitch <epicsInt32> (pIn, pOut);
          break;
        case NDUInt32:
          convertTypeSwitch <epicsUInt32> (pIn, pOut);
          break;
        case NDFloat32:
          convertTypeSwitch <epicsFloat32> (pIn, pOut);
          break;
        case NDFloat64:
          convertTypeSwitch <epicsFloat64> (pIn, pOut);
          break;
//.........这里部分代码省略.........
开发者ID:EdWarrick,项目名称:ADCore,代码行数:101,代码来源:NDArrayPool.cpp


注:本文中的NDAttribute类示例由纯净天空整理自Github/MSDocs等开源代码及文档管理平台,相关代码片段筛选自各路编程大神贡献的开源项目,源码版权归原作者所有,传播和使用请参考对应项目的License;未经允许,请勿转载。