예제 #1
0
SANE_Status
sane_get_parameters (SANE_Handle handle, SANE_Parameters * params)
{
  Abaton_Scanner *s = handle;

  DBG (FLOW_CONTROL, "Entering sane_get_parameters\n");
  calc_parameters (s);


  if (params)
    *params = s->params;
  return SANE_STATUS_GOOD;
}
예제 #2
0
SANE_Status
sane_get_parameters (SANE_Handle handle, SANE_Parameters * params)
{
  Mustek_Usb_Scanner *s = handle;
  SANE_Status status;

  DBG (5, "sane_get_parameters: start\n");

  RIE (calc_parameters (s));
  if (params)
    *params = s->params;

  DBG (5, "sane_get_parameters: exit\n");

  return SANE_STATUS_GOOD;
}
예제 #3
0
static SANE_Status
mode_update (SANE_Handle handle, char *val)
{
  Abaton_Scanner *s = handle;

  if (!strcmp (val, SANE_VALUE_SCAN_MODE_LINEART))
    {
      DISABLE (OPT_BRIGHTNESS);
      DISABLE (OPT_CONTRAST);
      ENABLE (OPT_THRESHOLD);
      DISABLE (OPT_HALFTONE_PATTERN);
    }
  else if (!strcmp (val, SANE_VALUE_SCAN_MODE_HALFTONE))
    {
      ENABLE (OPT_BRIGHTNESS);
      ENABLE (OPT_CONTRAST);
      DISABLE (OPT_THRESHOLD);
      ENABLE (OPT_HALFTONE_PATTERN);
    }
  else if (!strcmp (val, "Gray16") || !strcmp (val, "Gray256"))
    {
      ENABLE (OPT_BRIGHTNESS);
      ENABLE (OPT_CONTRAST);
      DISABLE (OPT_THRESHOLD);
      DISABLE (OPT_HALFTONE_PATTERN);
    }				/* End of Gray */
  else
    {
      DBG (ERROR_MESSAGE, "Invalid mode %s\n", (char *) val);
      return SANE_STATUS_INVAL;
    }

  calc_parameters (s);

  return SANE_STATUS_GOOD;
}
예제 #4
0
static SANE_Status
init_options (Mustek_Usb_Scanner * s)
{
  SANE_Int option;
  SANE_Status status;

  DBG (5, "init_options: start\n");

  memset (s->opt, 0, sizeof (s->opt));
  memset (s->val, 0, sizeof (s->val));

  for (option = 0; option < NUM_OPTIONS; ++option)
    {
      s->opt[option].size = sizeof (SANE_Word);
      s->opt[option].cap = SANE_CAP_SOFT_SELECT | SANE_CAP_SOFT_DETECT;
    }
  s->opt[OPT_NUM_OPTS].name = SANE_NAME_NUM_OPTIONS;
  s->opt[OPT_NUM_OPTS].title = SANE_TITLE_NUM_OPTIONS;
  s->opt[OPT_NUM_OPTS].desc = SANE_DESC_NUM_OPTIONS;
  s->opt[OPT_NUM_OPTS].type = SANE_TYPE_INT;
  s->opt[OPT_NUM_OPTS].cap = SANE_CAP_SOFT_DETECT;
  s->val[OPT_NUM_OPTS].w = NUM_OPTIONS;

  /* "Mode" group: */
  s->opt[OPT_MODE_GROUP].title = SANE_I18N ("Scan Mode");
  s->opt[OPT_MODE_GROUP].desc = "";
  s->opt[OPT_MODE_GROUP].type = SANE_TYPE_GROUP;
  s->opt[OPT_MODE_GROUP].size = 0;
  s->opt[OPT_MODE_GROUP].cap = 0;
  s->opt[OPT_MODE_GROUP].constraint_type = SANE_CONSTRAINT_NONE;

  /* scan mode */
  mode_list[0] = SANE_VALUE_SCAN_MODE_COLOR;
  mode_list[1] = SANE_VALUE_SCAN_MODE_GRAY;
  mode_list[2] = SANE_VALUE_SCAN_MODE_LINEART;
  mode_list[3] = NULL;

  s->opt[OPT_MODE].name = SANE_NAME_SCAN_MODE;
  s->opt[OPT_MODE].title = SANE_TITLE_SCAN_MODE;
  s->opt[OPT_MODE].desc = SANE_DESC_SCAN_MODE;
  s->opt[OPT_MODE].type = SANE_TYPE_STRING;
  s->opt[OPT_MODE].constraint_type = SANE_CONSTRAINT_STRING_LIST;
  s->opt[OPT_MODE].size = max_string_size (mode_list);
  s->opt[OPT_MODE].constraint.string_list = mode_list;
  s->val[OPT_MODE].s = strdup (mode_list[1]);

  /* resolution */
  s->opt[OPT_RESOLUTION].name = SANE_NAME_SCAN_RESOLUTION;
  s->opt[OPT_RESOLUTION].title = SANE_TITLE_SCAN_RESOLUTION;
  s->opt[OPT_RESOLUTION].desc = SANE_DESC_SCAN_RESOLUTION;
  s->opt[OPT_RESOLUTION].type = SANE_TYPE_FIXED;
  s->opt[OPT_RESOLUTION].unit = SANE_UNIT_DPI;
  s->opt[OPT_RESOLUTION].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_RESOLUTION].constraint.range = &s->hw->dpi_range;
  s->val[OPT_RESOLUTION].w = s->hw->dpi_range.min;
  if (s->hw->chip->scanner_type == MT_600CU)
    s->hw->dpi_range.max = SANE_FIX (600);
  else
    s->hw->dpi_range.max = SANE_FIX (1200);

  /* preview */
  s->opt[OPT_PREVIEW].name = SANE_NAME_PREVIEW;
  s->opt[OPT_PREVIEW].title = SANE_TITLE_PREVIEW;
  s->opt[OPT_PREVIEW].desc = SANE_DESC_PREVIEW;
  s->opt[OPT_PREVIEW].cap = SANE_CAP_SOFT_DETECT | SANE_CAP_SOFT_SELECT;
  s->opt[OPT_PREVIEW].type = SANE_TYPE_BOOL;
  s->val[OPT_PREVIEW].w = SANE_FALSE;

  /* "Geometry" group: */
  s->opt[OPT_GEOMETRY_GROUP].title = SANE_I18N ("Geometry");
  s->opt[OPT_GEOMETRY_GROUP].desc = "";
  s->opt[OPT_GEOMETRY_GROUP].type = SANE_TYPE_GROUP;
  s->opt[OPT_GEOMETRY_GROUP].cap = SANE_CAP_ADVANCED;
  s->opt[OPT_GEOMETRY_GROUP].size = 0;
  s->opt[OPT_GEOMETRY_GROUP].constraint_type = SANE_CONSTRAINT_NONE;

  /* top-left x */
  s->opt[OPT_TL_X].name = SANE_NAME_SCAN_TL_X;
  s->opt[OPT_TL_X].title = SANE_TITLE_SCAN_TL_X;
  s->opt[OPT_TL_X].desc = SANE_DESC_SCAN_TL_X;
  s->opt[OPT_TL_X].type = SANE_TYPE_FIXED;
  s->opt[OPT_TL_X].unit = SANE_UNIT_MM;
  s->opt[OPT_TL_X].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_TL_X].constraint.range = &s->hw->x_range;
  s->val[OPT_TL_X].w = 0;

  /* top-left y */
  s->opt[OPT_TL_Y].name = SANE_NAME_SCAN_TL_Y;
  s->opt[OPT_TL_Y].title = SANE_TITLE_SCAN_TL_Y;
  s->opt[OPT_TL_Y].desc = SANE_DESC_SCAN_TL_Y;
  s->opt[OPT_TL_Y].type = SANE_TYPE_FIXED;
  s->opt[OPT_TL_Y].unit = SANE_UNIT_MM;
  s->opt[OPT_TL_Y].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_TL_Y].constraint.range = &s->hw->y_range;
  s->val[OPT_TL_Y].w = 0;

  /* bottom-right x */
  s->opt[OPT_BR_X].name = SANE_NAME_SCAN_BR_X;
  s->opt[OPT_BR_X].title = SANE_TITLE_SCAN_BR_X;
  s->opt[OPT_BR_X].desc = SANE_DESC_SCAN_BR_X;
  s->opt[OPT_BR_X].type = SANE_TYPE_FIXED;
  s->opt[OPT_BR_X].unit = SANE_UNIT_MM;
  s->opt[OPT_BR_X].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_BR_X].constraint.range = &s->hw->x_range;
  s->val[OPT_BR_X].w = s->hw->x_range.max;

  /* bottom-right y */
  s->opt[OPT_BR_Y].name = SANE_NAME_SCAN_BR_Y;
  s->opt[OPT_BR_Y].title = SANE_TITLE_SCAN_BR_Y;
  s->opt[OPT_BR_Y].desc = SANE_DESC_SCAN_BR_Y;
  s->opt[OPT_BR_Y].type = SANE_TYPE_FIXED;
  s->opt[OPT_BR_Y].unit = SANE_UNIT_MM;
  s->opt[OPT_BR_Y].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_BR_Y].constraint.range = &s->hw->y_range;
  s->val[OPT_BR_Y].w = s->hw->y_range.max;

  /* "Enhancement" group: */
  s->opt[OPT_ENHANCEMENT_GROUP].title = SANE_I18N ("Enhancement");
  s->opt[OPT_ENHANCEMENT_GROUP].desc = "";
  s->opt[OPT_ENHANCEMENT_GROUP].type = SANE_TYPE_GROUP;
  s->opt[OPT_ENHANCEMENT_GROUP].size = 0;
  s->opt[OPT_ENHANCEMENT_GROUP].cap = 0;
  s->opt[OPT_ENHANCEMENT_GROUP].constraint_type = SANE_CONSTRAINT_NONE;

  /* threshold */
  s->opt[OPT_THRESHOLD].name = SANE_NAME_THRESHOLD;
  s->opt[OPT_THRESHOLD].title = SANE_TITLE_THRESHOLD;
  s->opt[OPT_THRESHOLD].desc = SANE_DESC_THRESHOLD;
  s->opt[OPT_THRESHOLD].type = SANE_TYPE_INT;
  s->opt[OPT_THRESHOLD].unit = SANE_UNIT_NONE;
  s->opt[OPT_THRESHOLD].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_THRESHOLD].constraint.range = &u8_range;
  s->opt[OPT_THRESHOLD].cap |= SANE_CAP_INACTIVE;
  s->val[OPT_THRESHOLD].w = 128;

  /* custom-gamma table */
  s->opt[OPT_CUSTOM_GAMMA].name = SANE_NAME_CUSTOM_GAMMA;
  s->opt[OPT_CUSTOM_GAMMA].title = SANE_TITLE_CUSTOM_GAMMA;
  s->opt[OPT_CUSTOM_GAMMA].desc = SANE_DESC_CUSTOM_GAMMA;
  s->opt[OPT_CUSTOM_GAMMA].type = SANE_TYPE_BOOL;
  s->val[OPT_CUSTOM_GAMMA].w = SANE_FALSE;

  /* gray gamma vector */
  s->opt[OPT_GAMMA_VECTOR].name = SANE_NAME_GAMMA_VECTOR;
  s->opt[OPT_GAMMA_VECTOR].title = SANE_TITLE_GAMMA_VECTOR;
  s->opt[OPT_GAMMA_VECTOR].desc = SANE_DESC_GAMMA_VECTOR;
  s->opt[OPT_GAMMA_VECTOR].type = SANE_TYPE_INT;
  s->opt[OPT_GAMMA_VECTOR].cap |= SANE_CAP_INACTIVE;
  s->opt[OPT_GAMMA_VECTOR].unit = SANE_UNIT_NONE;
  s->opt[OPT_GAMMA_VECTOR].size = 256 * sizeof (SANE_Word);
  s->opt[OPT_GAMMA_VECTOR].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_GAMMA_VECTOR].constraint.range = &u8_range;
  s->val[OPT_GAMMA_VECTOR].wa = &s->gray_gamma_table[0];

  /* red gamma vector */
  s->opt[OPT_GAMMA_VECTOR_R].name = SANE_NAME_GAMMA_VECTOR_R;
  s->opt[OPT_GAMMA_VECTOR_R].title = SANE_TITLE_GAMMA_VECTOR_R;
  s->opt[OPT_GAMMA_VECTOR_R].desc = SANE_DESC_GAMMA_VECTOR_R;
  s->opt[OPT_GAMMA_VECTOR_R].type = SANE_TYPE_INT;
  s->opt[OPT_GAMMA_VECTOR_R].cap |= SANE_CAP_INACTIVE;
  s->opt[OPT_GAMMA_VECTOR_R].unit = SANE_UNIT_NONE;
  s->opt[OPT_GAMMA_VECTOR_R].size = 256 * sizeof (SANE_Word);
  s->opt[OPT_GAMMA_VECTOR_R].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_GAMMA_VECTOR_R].constraint.range = &u8_range;
  s->val[OPT_GAMMA_VECTOR_R].wa = &s->red_gamma_table[0];

  /* green gamma vector */
  s->opt[OPT_GAMMA_VECTOR_G].name = SANE_NAME_GAMMA_VECTOR_G;
  s->opt[OPT_GAMMA_VECTOR_G].title = SANE_TITLE_GAMMA_VECTOR_G;
  s->opt[OPT_GAMMA_VECTOR_G].desc = SANE_DESC_GAMMA_VECTOR_G;
  s->opt[OPT_GAMMA_VECTOR_G].type = SANE_TYPE_INT;
  s->opt[OPT_GAMMA_VECTOR_G].cap |= SANE_CAP_INACTIVE;
  s->opt[OPT_GAMMA_VECTOR_G].unit = SANE_UNIT_NONE;
  s->opt[OPT_GAMMA_VECTOR_G].size = 256 * sizeof (SANE_Word);
  s->opt[OPT_GAMMA_VECTOR_G].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_GAMMA_VECTOR_G].constraint.range = &u8_range;
  s->val[OPT_GAMMA_VECTOR_G].wa = &s->green_gamma_table[0];

  /* blue gamma vector */
  s->opt[OPT_GAMMA_VECTOR_B].name = SANE_NAME_GAMMA_VECTOR_B;
  s->opt[OPT_GAMMA_VECTOR_B].title = SANE_TITLE_GAMMA_VECTOR_B;
  s->opt[OPT_GAMMA_VECTOR_B].desc = SANE_DESC_GAMMA_VECTOR_B;
  s->opt[OPT_GAMMA_VECTOR_B].type = SANE_TYPE_INT;
  s->opt[OPT_GAMMA_VECTOR_B].cap |= SANE_CAP_INACTIVE;
  s->opt[OPT_GAMMA_VECTOR_B].unit = SANE_UNIT_NONE;
  s->opt[OPT_GAMMA_VECTOR_B].size = 256 * sizeof (SANE_Word);
  s->opt[OPT_GAMMA_VECTOR_B].constraint_type = SANE_CONSTRAINT_RANGE;
  s->opt[OPT_GAMMA_VECTOR_B].constraint.range = &u8_range;
  s->val[OPT_GAMMA_VECTOR_B].wa = &s->blue_gamma_table[0];

  RIE (calc_parameters (s));

  DBG (5, "init_options: exit\n");
  return SANE_STATUS_GOOD;
}
예제 #5
0
SANE_Status
sane_start (SANE_Handle handle)
{
  Mustek_Usb_Scanner *s = handle;
  SANE_Status status;
  SANE_String val;
  Colormode color_mode;
  SANE_Word dpi, x, y, width, height;

  DBG (5, "sane_start: start\n");

  /* First make sure we have a current parameter set.  Some of the
     parameters will be overwritten below, but that's OK.  */

  s->total_bytes = 0;
  s->total_lines = 0;
  RIE (calc_parameters (s));

  if (s->width_dots <= 0)
    {
      DBG (0, "sane_start: top left x > bottom right x --- exiting\n");
      return SANE_STATUS_INVAL;
    }
  if (s->height_dots <= 0)
    {
      DBG (0, "sane_start: top left y > bottom right y --- exiting\n");
      return SANE_STATUS_INVAL;
    }


  val = s->val[OPT_MODE].s;
  if (!strcmp (val, SANE_VALUE_SCAN_MODE_LINEART))
    color_mode = GRAY8;
  else if (!strcmp (val, SANE_VALUE_SCAN_MODE_GRAY))
    color_mode = GRAY8;
  else				/* Color */
    color_mode = RGB24;

  dpi = SANE_UNFIX (s->val[OPT_RESOLUTION].w);
  x = s->tl_x_dots;
  y = s->tl_y_dots;
  width = s->width_dots;
  height = s->height_dots;

  if (!s->hw->is_prepared)
    {
      RIE (usb_high_scan_prepare (s->hw));
      RIE (usb_high_scan_reset (s->hw));
    }
  RIE (usb_high_scan_set_threshold (s->hw, 128));
  RIE (usb_high_scan_embed_gamma (s->hw, NULL));
  RIE (usb_high_scan_suggest_parameters (s->hw, dpi, x, y, width, height,
					 color_mode));
  RIE (usb_high_scan_setup_scan (s->hw, s->hw->scan_mode, s->hw->x_dpi,
				 s->hw->y_dpi, 0, s->hw->x, s->hw->y,
				 s->hw->width));

  DBG (3, "sane_start: wanted: dpi=%d, x=%d, y=%d, width=%d, height=%d, "
       "scan_mode=%d\n", dpi, x, y, width, height, color_mode);
  DBG (3, "sane_start: got: x_dpi=%d, y_dpi=%d, x=%d, y=%d, width=%d, "
       "height=%d, scan_mode=%d\n", s->hw->x_dpi, s->hw->y_dpi, s->hw->x,
       s->hw->y, s->hw->width, s->hw->height, s->hw->scan_mode);

  s->scanning = SANE_TRUE;
  s->read_rows = s->hw->height;
  s->hw->line_switch = s->hw->height;
  s->hw->line_offset = 0;
  s->hw->scan_buffer_len = 0;

  DBG (5, "sane_start: exit\n");
  return SANE_STATUS_GOOD;
}
예제 #6
0
SANE_Status
sane_control_option (SANE_Handle handle, SANE_Int option,
		     SANE_Action action, void *val, SANE_Int * info)
{
  Mustek_Usb_Scanner *s = handle;
  SANE_Status status;
  SANE_Word cap;
  SANE_Int myinfo = 0;

  DBG (5, "sane_control_option: start: action = %s, option = %s (%d)\n",
       (action == SANE_ACTION_GET_VALUE) ? "get" :
       (action == SANE_ACTION_SET_VALUE) ? "set" :
       (action == SANE_ACTION_SET_AUTO) ? "set_auto" : "unknown",
       s->opt[option].name, option);

  if (info)
    *info = 0;

  if (s->scanning)
    {
      DBG (1, "sane_control_option: don't call this function while "
	   "scanning\n");
      return SANE_STATUS_DEVICE_BUSY;
    }

  if (option >= NUM_OPTIONS || option < 0)
    {
      DBG (1, "sane_control_option: option %d >= NUM_OPTIONS || option < 0\n",
	   option);
      return SANE_STATUS_INVAL;
    }

  cap = s->opt[option].cap;

  if (!SANE_OPTION_IS_ACTIVE (cap))
    {
      DBG (2, "sane_control_option: option %d is inactive\n", option);
      return SANE_STATUS_INVAL;
    }

  if (action == SANE_ACTION_GET_VALUE)
    {
      switch (option)
	{
	  /* word options: */
	case OPT_NUM_OPTS:
	case OPT_RESOLUTION:
	case OPT_PREVIEW:
	case OPT_TL_X:
	case OPT_TL_Y:
	case OPT_BR_X:
	case OPT_BR_Y:
	case OPT_THRESHOLD:
	case OPT_CUSTOM_GAMMA:
	  *(SANE_Word *) val = s->val[option].w;
	  break;
	  /* word-array options: */
	case OPT_GAMMA_VECTOR:
	case OPT_GAMMA_VECTOR_R:
	case OPT_GAMMA_VECTOR_G:
	case OPT_GAMMA_VECTOR_B:
	  memcpy (val, s->val[option].wa, s->opt[option].size);
	  break;
	  /* string options: */
	case OPT_MODE:
	  strcpy (val, s->val[option].s);
	  break;
	default:
	  DBG (2, "sane_control_option: can't get unknown option %d\n",
	       option);
	}
    }
  else if (action == SANE_ACTION_SET_VALUE)
    {
      if (!SANE_OPTION_IS_SETTABLE (cap))
	{
	  DBG (2, "sane_control_option: option %d is not settable\n", option);
	  return SANE_STATUS_INVAL;
	}

      status = sanei_constrain_value (s->opt + option, val, &myinfo);

      if (status != SANE_STATUS_GOOD)
	{
	  DBG (2, "sane_control_option: sanei_constrain_value returned %s\n",
	       sane_strstatus (status));
	  return status;
	}

      switch (option)
	{
	  /* (mostly) side-effect-free word options: */
	case OPT_RESOLUTION:
	case OPT_TL_X:
	case OPT_TL_Y:
	case OPT_BR_X:
	case OPT_BR_Y:
	  s->val[option].w = *(SANE_Word *) val;
	  RIE (calc_parameters (s));
	  myinfo |= SANE_INFO_RELOAD_PARAMS;
	  break;
	case OPT_THRESHOLD:
	  s->val[option].w = *(SANE_Word *) val;
	  break;
	  /* Boolean */
	case OPT_PREVIEW:
	  s->val[option].w = *(SANE_Bool *) val;
	  break;
	  /* side-effect-free word-array options: */
	case OPT_GAMMA_VECTOR:
	case OPT_GAMMA_VECTOR_R:
	case OPT_GAMMA_VECTOR_G:
	case OPT_GAMMA_VECTOR_B:
	  memcpy (s->val[option].wa, val, s->opt[option].size);
	  check_gamma_table (s->val[option].wa);
	  break;
	case OPT_CUSTOM_GAMMA:
	  s->val[OPT_CUSTOM_GAMMA].w = *(SANE_Word *) val;
	  myinfo |= SANE_INFO_RELOAD_OPTIONS;
	  if (s->val[OPT_CUSTOM_GAMMA].w == SANE_TRUE)
	    {
	      s->red_table = s->red_gamma_table;
	      s->green_table = s->green_gamma_table;
	      s->blue_table = s->blue_gamma_table;
	      s->gray_table = s->gray_gamma_table;
	      if (strcmp (s->val[OPT_MODE].s, SANE_VALUE_SCAN_MODE_GRAY) == 0)
		s->opt[OPT_GAMMA_VECTOR].cap &= ~SANE_CAP_INACTIVE;
	      else if (strcmp (s->val[OPT_MODE].s, SANE_VALUE_SCAN_MODE_COLOR) == 0)
		{
		  s->opt[OPT_GAMMA_VECTOR].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_R].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_G].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_B].cap &= ~SANE_CAP_INACTIVE;
		}
	    }
	  else
	    {
	      s->red_table = s->linear_gamma_table;
	      s->green_table = s->linear_gamma_table;
	      s->blue_table = s->linear_gamma_table;
	      s->gray_table = s->linear_gamma_table;
	      s->opt[OPT_GAMMA_VECTOR].cap |= SANE_CAP_INACTIVE;
	      s->opt[OPT_GAMMA_VECTOR_R].cap |= SANE_CAP_INACTIVE;
	      s->opt[OPT_GAMMA_VECTOR_G].cap |= SANE_CAP_INACTIVE;
	      s->opt[OPT_GAMMA_VECTOR_B].cap |= SANE_CAP_INACTIVE;
	    }
	  break;
	case OPT_MODE:
	  if (s->val[option].s)
	    free (s->val[option].s);
	  s->val[option].s = strdup (val);

	  RIE (calc_parameters (s));

	  s->opt[OPT_THRESHOLD].cap |= SANE_CAP_INACTIVE;
	  s->opt[OPT_CUSTOM_GAMMA].cap |= SANE_CAP_INACTIVE;
	  s->opt[OPT_GAMMA_VECTOR].cap |= SANE_CAP_INACTIVE;
	  s->opt[OPT_GAMMA_VECTOR_R].cap |= SANE_CAP_INACTIVE;
	  s->opt[OPT_GAMMA_VECTOR_G].cap |= SANE_CAP_INACTIVE;
	  s->opt[OPT_GAMMA_VECTOR_B].cap |= SANE_CAP_INACTIVE;

	  if (strcmp (val, SANE_VALUE_SCAN_MODE_LINEART) == 0)
	    {
	      s->opt[OPT_THRESHOLD].cap &= ~SANE_CAP_INACTIVE;
	    }
	  else
	    {
	      s->opt[OPT_CUSTOM_GAMMA].cap &= ~SANE_CAP_INACTIVE;
	      if (s->val[OPT_CUSTOM_GAMMA].w == SANE_TRUE)
		{
		  s->opt[OPT_GAMMA_VECTOR].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_R].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_G].cap &= ~SANE_CAP_INACTIVE;
		  s->opt[OPT_GAMMA_VECTOR_B].cap &= ~SANE_CAP_INACTIVE;
		}
	    }
	  myinfo |= SANE_INFO_RELOAD_OPTIONS | SANE_INFO_RELOAD_PARAMS;
	  break;
	default:
	  DBG (2, "sane_control_option: can't set unknown option %d\n",
	       option);
	}
    }
  else
    {
      DBG (2, "sane_control_option: unknown action %d for option %d\n",
	   action, option);
      return SANE_STATUS_INVAL;
    }
  if (info)
    *info = myinfo;

  DBG (5, "sane_control_option: exit\n");
  return SANE_STATUS_GOOD;
}
예제 #7
0
SANE_Status
sane_start (SANE_Handle handle)
{
  Abaton_Scanner *s = handle;
  SANE_Status status;

  /* First make sure we have a current parameter set.  Some of the
     parameters will be overwritten below, but that's OK.  */

  calc_parameters (s);

  if (s->fd < 0)
    {
      /* this is the first (and maybe only) pass... */

      status = sanei_scsi_open (s->hw->sane.name, &s->fd, sense_handler, 0);
      if (status != SANE_STATUS_GOOD)
	{
	  DBG (ERROR_MESSAGE, "open: open of %s failed: %s\n",
	       s->hw->sane.name, sane_strstatus (status));
	  return status;
	}
    }

  status = wait_ready (s->fd);
  if (status != SANE_STATUS_GOOD)
    {
      DBG (ERROR_MESSAGE, "open: wait_ready() failed: %s\n",
	   sane_strstatus (status));
      goto stop_scanner_and_return;
    }

  status = request_sense (s);
  if (status != SANE_STATUS_GOOD)
    {
      DBG (ERROR_MESSAGE, "sane_start: request_sense revealed error: %s\n",
	   sane_strstatus (status));
      goto stop_scanner_and_return;
    }

  status = set_window (s);
  if (status != SANE_STATUS_GOOD)
    {
      DBG (ERROR_MESSAGE, "open: set scan area command failed: %s\n",
	   sane_strstatus (status));
      goto stop_scanner_and_return;
    }

  s->scanning = SANE_TRUE;
  s->AbortedByUser = SANE_FALSE;

  status = start_scan (s);
  if (status != SANE_STATUS_GOOD)
    goto stop_scanner_and_return;

  return SANE_STATUS_GOOD;

stop_scanner_and_return:
  s->scanning = SANE_FALSE;
  s->AbortedByUser = SANE_FALSE;
  return status;
}
예제 #8
0
SANE_Status
sane_control_option (SANE_Handle handle, SANE_Int option,
		     SANE_Action action, void *val, SANE_Int * info)
{
  Abaton_Scanner *s = handle;
  SANE_Status status;
  SANE_Word cap;


  if (option < 0 || option >= NUM_OPTIONS)
    return SANE_STATUS_INVAL;

  if (info != NULL)
    *info = 0;

  if (s->scanning)
    return SANE_STATUS_DEVICE_BUSY;

  cap = s->opt[option].cap;

  if (!SANE_OPTION_IS_ACTIVE (cap))
    return SANE_STATUS_INVAL;

  if (action == SANE_ACTION_GET_VALUE)
    {
      switch (option)
	{
	  /* word options: */
	case OPT_NUM_OPTS:
	case OPT_X_RESOLUTION:
	case OPT_Y_RESOLUTION:
	case OPT_RESOLUTION_BIND:
	case OPT_PREVIEW:
	case OPT_TL_X:
	case OPT_TL_Y:
	case OPT_BR_X:
	case OPT_BR_Y:
	case OPT_BRIGHTNESS:
	case OPT_CONTRAST:
	case OPT_THRESHOLD:
	case OPT_NEGATIVE:
	case OPT_MIRROR:
	  *(SANE_Word *) val = s->val[option].w;
	  return SANE_STATUS_GOOD;

	  /* string options */

	case OPT_MODE:
	case OPT_HALFTONE_PATTERN:
	  status = sanei_constrain_value (s->opt + option, s->val[option].s,
					  info);
	  strcpy (val, s->val[option].s);	  
	  return SANE_STATUS_GOOD;
	}
    }
  else if (action == SANE_ACTION_SET_VALUE)
    {
      if (!SANE_OPTION_IS_SETTABLE (cap))
	return SANE_STATUS_INVAL;

      status = sanei_constrain_value (s->opt + option, val, info);

      if (status != SANE_STATUS_GOOD)
	return status;


      switch (option)
	{
	  /* resolution should be uniform for previews, or when the
	     user says so. */
	case OPT_PREVIEW:
	  s->val[option].w = *(SANE_Word *) val;
	  if (*(SANE_Word *) val) {
	    s->val[OPT_Y_RESOLUTION].w = s->val[OPT_X_RESOLUTION].w;
	    if (info)
	      *info |= SANE_INFO_RELOAD_OPTIONS;
	  }
	  /* always recalculate! */
	  calc_parameters (s);
	  if (info)
	    *info |= SANE_INFO_RELOAD_PARAMS;
	  return SANE_STATUS_GOOD;
	    
	case OPT_RESOLUTION_BIND:
	  s->val[option].w = *(SANE_Word *) val;
	  if (*(SANE_Word *) val) {
	    s->val[OPT_Y_RESOLUTION].w = s->val[OPT_X_RESOLUTION].w;
	    calc_parameters (s);
	    if (info)
	      *info |= SANE_INFO_RELOAD_PARAMS |
		SANE_INFO_RELOAD_OPTIONS;
	  }
	  return SANE_STATUS_GOOD;
	  
	case OPT_X_RESOLUTION:
	  if (s->val[OPT_PREVIEW].w || s->val[OPT_RESOLUTION_BIND].w) {
	    s->val[OPT_Y_RESOLUTION].w = *(SANE_Word *)val;
	    if (info)
	      *info |= SANE_INFO_RELOAD_OPTIONS;
	  }
	  s->val[option].w = *(SANE_Word *) val;
	  calc_parameters (s);
	  if (info)
	    *info |= SANE_INFO_RELOAD_PARAMS;
	  return SANE_STATUS_GOOD;

	case OPT_Y_RESOLUTION:
	  if (s->val[OPT_PREVIEW].w || s->val[OPT_RESOLUTION_BIND].w) {
	    s->val[OPT_X_RESOLUTION].w = *(SANE_Word *)val;
	    if (info)
	      *info |= SANE_INFO_RELOAD_OPTIONS;
	  }
	  s->val[option].w = *(SANE_Word *) val;
	  calc_parameters (s);
	  if (info)
	    *info |= SANE_INFO_RELOAD_PARAMS;
	  return SANE_STATUS_GOOD;

	  /* these ones don't have crazy side effects */
	case OPT_TL_X:
	case OPT_TL_Y:
	case OPT_BR_Y:
	  s->val[option].w = *(SANE_Word *) val;
	  calc_parameters (s);
	  if (info)
	    *info |= SANE_INFO_RELOAD_PARAMS;
	  return SANE_STATUS_GOOD;

	  /* this one is somewhat imprecise */
	case OPT_BR_X:
	  s->val[option].w = *(SANE_Word *) val;
	  calc_parameters (s);
	  if (info)
	    *info |= SANE_INFO_RELOAD_PARAMS
	      | SANE_INFO_INEXACT;	  
	  return SANE_STATUS_GOOD;

	  /* no side-effects whatsoever */
	case OPT_BRIGHTNESS:
	case OPT_CONTRAST:
	case OPT_THRESHOLD:
	case OPT_NEGATIVE:
	case OPT_MIRROR:

	  s->val[option].w = *(SANE_Word *) val;
	  return SANE_STATUS_GOOD;

	  /* string options */
	case OPT_HALFTONE_PATTERN:
	  if (info)
	    *info |= SANE_INFO_RELOAD_OPTIONS;
	  if (s->val[option].s)
	    free (s->val[option].s);
	  s->val[option].s = strdup (val);
	  return SANE_STATUS_GOOD;
	  
	case OPT_MODE:
	  status = mode_update (s, val);
	  if (status != SANE_STATUS_GOOD)
	    return status;
	  if (s->val[option].s)
	    free (s->val[option].s);
	  s->val[option].s = strdup (val);

	  if (info)
	    *info |= SANE_INFO_RELOAD_OPTIONS | SANE_INFO_RELOAD_PARAMS;
	  return SANE_STATUS_GOOD;
	}			/* End of switch */
    }				/* End of SET_VALUE */
  return SANE_STATUS_INVAL;
}