Contact me: hankecnc@gmail.com

没有开关的归位?(仅限物理终点站) #746

推推 grbl 3年前 (2023-01-23) 272次浏览

打开
SketchThis 打开了这个问题 2019 年 10 月 24 日 · 10 条评论
打开

没有开关的归位?(仅限物理终点站)#746

SketchThis 打开了这个问题 2019 年 10 月 24 日 · 10 条评论

注释

没有开关的归位?(仅限物理终点站) #746

正如标题所说,是否可以在没有限位开关的情况下安装一台 GRBL 机器?

让我解释一下:我有一个我正在转换的 CNC,它通过将每个轴慢跑到比它实际所能到达的更远的位置来自我定位。

为了让每个轴归位,在 Z 零、X 12 和 Y 12 处有一个硬停。

机器的最大 Z 行程为 3 英寸,因此在归位时它会慢跑 4 英寸并到达终点。它后退 0.125″ 并在那里归零。

X 和 Y 也一样,它们慢跑到 13 英寸(比最大行程多 1″),所以它们到达终点。在 13″ 移动之后,它们慢跑到负 12″ 并在那里归零。

是否可以在 GRBL 的本地归巢程序中设置类似的东西?我确定我会使用本机 G 代码命令手动执行此操作,但我想让归位按钮真正起作用……

没有开关的归位?(仅限物理终点站) #746 Sketch 这个 改标题了 没有开关的归位(仅限物理端点) 没有开关的归位?(仅限物理终点站) 2019 年 10 月 24 日
没有开关的归位?(仅限物理终点站) #746

嗯……这真的有点粗略。我认为你最好在终点站添加限位开关。

但是,如果你真的、真的必须……看看 limits.c;特别是 limits_go_home()。

您需要做的是移除所有检查限位开关的东西,并在找到限位后执行拉动动作。

这是完全未经测试的;所以可能行不通——但是,我认为它应该看起来像这样:

void limits_go_home(uint8_t cycle_mask)
{
  if (sys.abort) { return; } // Block if system reset has been issued.

  // Initialize plan data struct for homing motion. Spindle and coolant are disabled.
  plan_line_data_t plan_data;
  plan_line_data_t *pl_data = &plan_data;
  memset(pl_data,0,sizeof(plan_line_data_t));
  pl_data->condition = (PL_COND_FLAG_SYSTEM_MOTION|PL_COND_FLAG_NO_FEED_OVERRIDE);
  #ifdef USE_LINE_NUMBERS
    pl_data->line_number = HOMING_CYCLE_LINE_NUMBER;
  #endif
  
  float max_travel = 0.0;
  uint8_t n_active_axis = 0;
  for (uint8_t idx=0; idx<N_AXIS; idx++)
  {
    if (bit_istrue(cycle_mask,bit(idx)))
    {
      // Set target based on max_travel setting. Ensure homing switches engaged with search scalar.
      // NOTE: settings.max_travel[] is stored as a negative value.
      max_travel = max(max_travel,(-HOMING_AXIS_SEARCH_SCALAR)*settings.max_travel[idx]);
      n_active_axis++;
    }
  }

  float target[N_AXIS];
  system_convert_array_steps_to_mpos(target,sys_position);

  for (idx=0; idx<N_AXIS; idx++)
  {
    // Set target location for active axes and setup computation for homing rate.
    if (bit_istrue(cycle_mask,bit(idx)))
    {
      sys_position[idx] = 0;
      
      // Set target direction based on cycle mask and homing cycle approach state.
      // NOTE: This happens to compile smaller than any other implementation tried.
      if (bit_istrue(settings.homing_dir_mask,bit(idx)))
      {
        target[idx] = -max_travel;
      }
      else
      {
        target[idx] = max_travel;
      }      
    }
  }

  // Perform homing cycle. Planner buffer should be empty, as required to initiate the homing cycle.
  float homing_rate = settings.homing_seek_rate;
  homing_rate *= sqrt(n_active_axis); // [sqrt(N_AXIS)] Adjust so individual axes all move at homing rate.
  pl_data->feed_rate = homing_rate; // Set current homing rate.
  plan_buffer_line(target, pl_data); // Bypass mc_line(). Directly plan homing motion.
  sys.step_control = STEP_CONTROL_EXECUTE_SYS_MOTION; // Set to execute homing motion and clear existing flags.
  st_prep_buffer(); // Prep and fill segment buffer from newly planned block.
  st_wake_up(); // Initiate motion

    do
    {
      st_prep_buffer(); // Check and prep segment buffer. NOTE: Should take no longer than 200us.

      // Exit routines: No time to run protocol_execute_realtime() in this loop.
      if (sys_rt_exec_state & (EXEC_SAFETY_DOOR | EXEC_RESET | EXEC_CYCLE_STOP))
      {
        uint8_t rt_exec = sys_rt_exec_state;
        // Homing failure condition: Reset issued during cycle.
        if (rt_exec & EXEC_RESET) { system_set_exec_alarm(EXEC_ALARM_HOMING_FAIL_RESET); }
        // Homing failure condition: Safety door was opened.
        if (rt_exec & EXEC_SAFETY_DOOR) { system_set_exec_alarm(EXEC_ALARM_HOMING_FAIL_DOOR); }
        // Homing failure condition: Limit switch not found during approach.
        if (sys_rt_exec_alarm)
        {
          mc_reset(); // Stop motors, if they are running.
          protocol_execute_realtime();
          return;
        }
      }
    } while (!(rt_exec & EXEC_CYCLE_STOP));

  // The active cycle axes should now be homed and machine limits have been located. By
  // default, Grbl defines machine space as all negative, as do most CNCs. Since limit stops
  // can be on either side of an axes, check and set axes machine zero appropriately.

  int32_t set_axis_position;
  // Set machine positions for homed limit switches. Don't update non-homed axes.
  for (idx=0; idx<N_AXIS; idx++)
  {
    // NOTE: settings.max_travel[] is stored as a negative value.
    if (cycle_mask & bit(idx))
    {
      #ifdef HOMING_FORCE_SET_ORIGIN
        set_axis_position = 0;
      #else
        if ( bit_istrue(settings.homing_dir_mask,bit(idx)) )
        {
          set_axis_position = lround((settings.max_travel[idx]+settings.homing_pulloff)*settings.steps_per_mm[idx]);
        }
        else
        {
          set_axis_position = lround(-settings.homing_pulloff*settings.steps_per_mm[idx]);
        }
      #endif

      sys_position[idx] = set_axis_position;
    }
  }
  sys.step_control = STEP_CONTROL_NORMAL_OP; // Return step control to normal operation.
}

没有开关的归位?(仅限物理终点站) #746

非常感谢你,我什至不知道从哪里开始寻找。我知道这听起来很粗略,但这正是这台机器是如何制造的。终点挡块实际上是可调的,因此您可以将它们精确地拨到您想要的位置。在归位程序中,机器以相当慢的速度偷偷靠近终点站。Z 仍然有一个触地板。

我会在那里闲逛,看看我能想出什么!

没有开关的归位?(仅限物理终点站) #746

好吧,我尝试编译该代码但失败了。我不完全(甚至部分!)理解这里的编程语言……

并不是说我想让任何人在这里为我做这项工作……但是有人愿意帮我深入研究一下,看看我是否能解决这个问题吗?

没有开关的归位?(仅限物理终点站) #746

抱歉 – 我发现了一些错别字。这已经过实际编译测试(但是,我没有硬件来测试它——我所做的一切都使用我自己的 Grbl-Mega 分支;并且有归位开关)。嗯……你真的、真的确定不想给它加一些限位开关吗?真的吗?


void limits_go_home(uint8_t cycle_mask)
{
  if (sys.abort) { return; } // Block if system reset has been issued.

  // Initialize plan data struct for homing motion. Spindle and coolant are disabled.
  plan_line_data_t plan_data;
  plan_line_data_t *pl_data = &plan_data;
  memset(pl_data,0,sizeof(plan_line_data_t));
  pl_data->condition = (PL_COND_FLAG_SYSTEM_MOTION|PL_COND_FLAG_NO_FEED_OVERRIDE);
  #ifdef USE_LINE_NUMBERS
    pl_data->line_number = HOMING_CYCLE_LINE_NUMBER;
  #endif
  
  float max_travel = 0.0;
  uint8_t n_active_axis = 0;
  for (uint8_t idx=0; idx<N_AXIS; idx++)
  {
    if (bit_istrue(cycle_mask,bit(idx)))
    {
      // Set target based on max_travel setting. Ensure homing switches engaged with search scalar.
      // NOTE: settings.max_travel[] is stored as a negative value.
      max_travel = max(max_travel,(-HOMING_AXIS_SEARCH_SCALAR)*settings.max_travel[idx]);
      n_active_axis++;
    }
  }

  float target[N_AXIS];
  system_convert_array_steps_to_mpos(target,sys_position);

  for (uint8_t idx=0; idx<N_AXIS; idx++)
  {
    // Set target location for active axes and setup computation for homing rate.
    if (bit_istrue(cycle_mask,bit(idx)))
    {
      sys_position[idx] = 0;
      
      // Set target direction based on cycle mask and homing cycle approach state.
      // NOTE: This happens to compile smaller than any other implementation tried.
      if (bit_istrue(settings.homing_dir_mask,bit(idx)))
      {
        target[idx] = -max_travel;
      }
      else
      {
        target[idx] = max_travel;
      }      
    }
  }

  // Perform homing cycle. Planner buffer should be empty, as required to initiate the homing cycle.
  float homing_rate = settings.homing_seek_rate;
  homing_rate *= sqrt(n_active_axis); // [sqrt(N_AXIS)] Adjust so individual axes all move at homing rate.
  pl_data->feed_rate = homing_rate; // Set current homing rate.
  plan_buffer_line(target, pl_data); // Bypass mc_line(). Directly plan homing motion.
  sys.step_control = STEP_CONTROL_EXECUTE_SYS_MOTION; // Set to execute homing motion and clear existing flags.
  st_prep_buffer(); // Prep and fill segment buffer from newly planned block.
  st_wake_up(); // Initiate motion

    uint8_t rt_exec;
    do
    {
      st_prep_buffer(); // Check and prep segment buffer. NOTE: Should take no longer than 200us.

      // Exit routines: No time to run protocol_execute_realtime() in this loop.
      rt_exec = sys_rt_exec_state;
      if (rt_exec & (EXEC_SAFETY_DOOR | EXEC_RESET | EXEC_CYCLE_STOP))
      {
        // Homing failure condition: Reset issued during cycle.
        if (rt_exec & EXEC_RESET) { system_set_exec_alarm(EXEC_ALARM_HOMING_FAIL_RESET); }
        // Homing failure condition: Safety door was opened.
        if (rt_exec & EXEC_SAFETY_DOOR) { system_set_exec_alarm(EXEC_ALARM_HOMING_FAIL_DOOR); }
        // Homing failure condition: Limit switch not found during approach.
        if (sys_rt_exec_alarm)
        {
          mc_reset(); // Stop motors, if they are running.
          protocol_execute_realtime();
          return;
        }
      }
    } while (!(rt_exec & EXEC_CYCLE_STOP));

  // The active cycle axes should now be homed and machine limits have been located. By
  // default, Grbl defines machine space as all negative, as do most CNCs. Since limit stops
  // can be on either side of an axes, check and set axes machine zero appropriately.

  int32_t set_axis_position;
  // Set machine positions for homed limit switches. Don't update non-homed axes.
  for (uint8_t idx=0; idx<N_AXIS; idx++)
  {
    // NOTE: settings.max_travel[] is stored as a negative value.
    if (cycle_mask & bit(idx))
    {
      #ifdef HOMING_FORCE_SET_ORIGIN
        set_axis_position = 0;
      #else
        if ( bit_istrue(settings.homing_dir_mask,bit(idx)) )
        {
          set_axis_position = lround((settings.max_travel[idx]+settings.homing_pulloff)*settings.steps_per_mm[idx]);
        }
        else
        {
          set_axis_position = lround(-settings.homing_pulloff*settings.steps_per_mm[idx]);
        }
      #endif

      sys_position[idx] = set_axis_position;
    }
  }
  sys.step_control = STEP_CONTROL_NORMAL_OP; // Return step control to normal operation.
}

没有开关的归位?(仅限物理终点站) #746

我知道没有 prox 开关听起来是个坏主意……但是这台机器的设计和制造是为了在没有它们的情况下工作:

https://store.handibot.com/collections/whats-new/products/handibot-smart-power-tool-v2-1-adventure-edition

每个轴上都有坚固的可调端挡块。

这就是我正在转换的。我已经移除了库存运动控制板,并已将其替换为 Arduino Uno。一切正常,我只需要解决这个归巢问题。我知道我可以在那里放一些接近开关,但如果可能的话我想跳过它们,这样机器就可以像出厂时一样工作。这样一来,无需以任何方式修改机器,就可以切换到 GRBL 控制,只需取下备用运动卡(单个 Db 37 连接器)并插入 Arduino。

我想知道我是否会遇到另一个问题。这台机器现在回家的方式是它一直慢跑 Z 并停止,然后慢跑到 X 8,停止,然后到 Y0 和到达停止点。然而,零位置在左下角。我的猜测是,除了更改限位开关的代码外,还需要对代码进行一些其他修改……

我不反对在这个东西上放置限位开关,我只是认为把它作为一个插头交换来做要酷得多。

这个周末我会试一试你的代码。谢谢你!

没有开关的归位?(仅限物理终点站) #746

好吧,正如您现在可能已经猜到的那样,我认为这是一个糟糕的工厂设计。?

可以使用标准参数设置归位方向——当我剥离归位例程时,我保留了那部分;查看有关设置归位的 wiki 文章以获取更多信息。只需用文章中提到的开关替换您的终点站。

没有开关的归位?(仅限物理终点站) #746

感谢您为此所做的工作!明天我回到店里时,我会试一试。

我知道我可以很容易地翻转归位方向……我想知道归零是如何工作的……三个终点挡块中有两个是零,但一个是最大行程……到目前为止我不知道当轴到达终点时我是否可以将机器坐标设置为非零数字,无论我是否使用 prox 开关它都不是..

没有开关的归位?(仅限物理终点站) #746

你应该能够用标准的方向控制设置做你想做的事;但如果你真的需要,你可以用这些线翻转它的方向:

      if (bit_istrue(settings.homing_dir_mask,bit(idx)))
      {
        target[idx] = -max_travel;
      }
      else
      {
        target[idx] = max_travel;
      }      

只需从一个 max_travel 中删除减号并将其添加到另一个。

归零是用这些行完成的:

        if ( bit_istrue(settings.homing_dir_mask,bit(idx)) )
        {
          set_axis_position = lround((settings.max_travel[idx]+settings.homing_pulloff)*settings.steps_per_mm[idx]);
        }
        else
        {
          set_axis_position = lround(-settings.homing_pulloff*settings.steps_per_mm[idx]);
        }
没有开关的归位?(仅限物理终点站) #746
作者

好的,我无法让它工作,它只是在归位期间挂起。因为我对编码了解不够,所以我没有真正的方法来解决问题,所以我认输了,我给它加了限位开关。:)

没有开关的归位?(仅限物理终点站) #746

好的,我无法让它工作,它只是在归位期间挂起。

奇怪……显然我无法测试它,我没有一台可以通过撞到挡块来回家的机器……但悬挂并不是我预期的结果之一。移动完成后,无论如何它都应该退出归巢循环。

具体来说,这个:while (!(rt_exec & EXEC_CYCLE_STOP));

无论如何 – 我确实认为从长远来看,使用限位开关会更好。

?

喜欢 (0)