docstr: Make a file containing object measurements
  
  object_names - sequence of names of the objects whose measurements
                 will be included
  image_set_numbers -  the image sets whose data gets extracted
  workspace - workspace containing the measurements
  settings_group - the settings group used to choose to make the file or
                   None if wants_everything
docstr_tok: ["Make","a","file","containing","object","measurements","object_names","-","sequence","of","names","of","the","objects","whose","measurements","will","be","included","image_set_numbers","-","the","image","sets","whose","data","gets","extracted","workspace","-","workspace","containing","the","measurements","settings_group","-","the","settings","group","used","to","choose","to","make","the","file","or","None","if","wants_everything"]
code: def make_object_file(
      self,
      object_names,
      image_set_numbers,
      workspace,
      settings_group=None,
  ):
      """Make a file containing object measurements
  
      object_names - sequence of names of the objects whose measurements
                     will be included
      image_set_numbers -  the image sets whose data gets extracted
      workspace - workspace containing the measurements
      settings_group - the settings group used to choose to make the file or
                       None if wants_everything
      """
      m = workspace.measurements
      file_name = self.make_objects_file_name(
          object_names[0],
          workspace,
          image_set_numbers[0],
          settings_group,
      )
      features = [
          (IMAGE, IMAGE_NUMBER),
          (object_names[0], OBJECT_NUMBER),
      ]
      columns = list(
          map(
              (lambda c: c[:2]),
              workspace.pipeline.get_measurement_columns(),
          )
      )
      if self.add_metadata.value:
          mdfeatures = [
              (IMAGE, name)
              for object_name, name in columns
              if name.startswith("Metadata_") and object_name == IMAGE
          ]
          mdfeatures.sort()
          features += mdfeatures
      if self.add_filepath.value:
          filefeatures = [
              (IMAGE, name)
              for object_name, name in columns
              if name.startswith(("PathName_", "FileName_"))
              and object_name == IMAGE
          ]
          filefeatures.sort()
          features += filefeatures
      for object_name in object_names:
          ofeatures = [
              feature
              for col_object, feature in columns
              if col_object == object_name
          ]
          ofeatures = self.filter_columns(ofeatures, object_name)
          ofeatures = [
              (object_name, feature_name) for feature_name in ofeatures
          ]
          ofeatures.sort()
          features += ofeatures
      fd = open(file_name, "w", newline="")
      try:
          writer = csv.writer(fd, delimiter=self.delimiter_char)
  
          #
          # We write the object names in the first row of headers if there are
          # multiple objects. Otherwise, we just write the feature names
          #
          for i in (0, 1) if len(object_names) > 1 else (1,):
              writer.writerow([x[i] for x in features])
  
          for img_number in image_set_numbers:
              object_count = numpy.max(
                  [
                      # If no objects are found in the image, we can't find the max of None - 4653
                      m.get_measurement(
                          IMAGE, "Count_%s" % name, img_number
                      )
                      or 0
                      for name in object_names
                  ]
              )
              object_count = (
                  int(object_count)
                  if object_count and not numpy.isnan(object_count)
                  else 0
              )
              columns = [
                  numpy.repeat(img_number, object_count)
                  if feature_name == IMAGE_NUMBER
                  else numpy.arange(1, object_count + 1)
                  if feature_name == OBJECT_NUMBER
                  else numpy.repeat(numpy.NAN, object_count)
                  if not m.has_feature(object_name, feature_name)
                  else numpy.repeat(
                      m.get_measurement(
                          IMAGE, feature_name, img_number
                      ),
                      object_count,
                  )
                  if object_name == IMAGE
                  else m.get_measurement(
                      object_name, feature_name, img_number
                  )
                  for object_name, feature_name in features
              ]
              for obj_index in range(object_count):
                  row = [
                      column[obj_index]
                      if (
                          column is not None
                          and obj_index < column.shape[0]
                      )
                      else numpy.NAN
                      for column in columns
                  ]
                  if self.nan_representation == NANS_AS_NULLS:
                      row = [
                          ""
                          if (field is None)
                          or (
                              numpy.isreal(field)
                              and not numpy.isfinite(field)
                          )
                          else field
                          for field in row
                      ]
                  writer.writerow(row)
      finally:
          fd.close()
  
imports: import base64
  import csv
  import logging
  import os
  import numpy
  from cellprofiler_core.constants.image import C_MD5_DIGEST, C_SCALING, C_HEIGHT, C_WIDTH
  from cellprofiler_core.constants.measurement import EXPERIMENT, IMAGE, AGG_MEAN, AGG_MEDIAN, AGG_STD_DEV, C_URL, C_PATH_NAME, C_FILE_NAME, NEIGHBORS, R_FIRST_IMAGE_NUMBER, R_SECOND_IMAGE_NUMBER, R_FIRST_OBJECT_NUMBER, R_SECOND_OBJECT_NUMBER
  from cellprofiler_core.constants.module import IO_FOLDER_CHOICE_HELP_TEXT, IO_WITH_METADATA_HELP_TEXT, USING_METADATA_HELP_REF, USING_METADATA_TAGS_REF
  from cellprofiler_core.constants.pipeline import EXIT_STATUS
  from cellprofiler_core.measurement import Measurements
  from cellprofiler_core.module import Module
  from cellprofiler_core.preferences import ABSOLUTE_FOLDER_NAME
  from cellprofiler_core.preferences import DEFAULT_INPUT_FOLDER_NAME
  from cellprofiler_core.preferences import DEFAULT_INPUT_SUBFOLDER_NAME
  from cellprofiler_core.preferences import DEFAULT_OUTPUT_FOLDER_NAME
  from cellprofiler_core.preferences import DEFAULT_OUTPUT_SUBFOLDER_NAME
  from cellprofiler_core.preferences import get_headless
  from cellprofiler_core.setting import Binary
  from cellprofiler_core.setting import Divider
  from cellprofiler_core.setting import Measurement
  from cellprofiler_core.setting import SettingsGroup
  from cellprofiler_core.setting import ValidationError
  from cellprofiler_core.setting.choice import CustomChoice, Choice
  from cellprofiler_core.setting.do_something import DoSomething, RemoveSettingButton
  from cellprofiler_core.setting.multichoice import MeasurementMultiChoice
  from cellprofiler_core.setting.subscriber import ImageSubscriber, LabelSubscriber
  from cellprofiler_core.setting.text import Directory, Text
  from cellprofiler_core.utilities.core.modules.load_data import is_file_name_feature, is_path_name_feature
  from cellprofiler_core.utilities.measurement import find_metadata_tokens, get_agg_measurement_name
  from cellprofiler.gui.help.content import MEASUREMENT_NAMING_HELP
label_desc: Use image node_id 28 for calling the ExportToSpreadsheet obj's underlying member method code with example usage: obj.make_object_file(object_names, image_set_numbers, workspace, settings_group) without return types