สมอง SML

คลังความรู้ / หน้าจอทีละจอ

#screens#pos

ตั้งค่าและควบคุมระบบขายหน้าร้าน POS (PosSetupAndControlScreen)

จอเดียวขนาดใหญ่ (4,948 บรรทัด) ที่ใช้เป็น "หน้าตั้งค่า POS" ของหลายเมนู ตัวจอมี 8 แท็บภายใน (PosSetupTabKey, :37-45): startup, machines, promotions, loyalty, qr, coupons, shifts, bills เมนูแต่ละตัวเลือกแท็บเริ่มต้นผ่าน createPosSetupScreen(menuKey, code, title, tab) ใน screenRegistry.tsx:133-145 หรือคำนวณจากชื่อเมนูด้วย resolveTabFromMenuKey (:134-145) ไม่มีแถบแท็บให้ผู้ใช้สลับเอง แต่ละเมนูเปิดมาเห็นเฉพาะส่วนของตัวเอง

จอนี้เป็นฝั่ง "ตั้งค่า" ของ SML Ai POS ส่วนจอขายจริงเป็นแอป Flutter ดู พื้นที่ทำงาน POS จอขายแคชเชียร์ (PosDemoWorkspace, เส้นทาง /pos), ตรรกะฝั่งเซิร์ฟเวอร์ดู POS ตั้งค่าร้าน/เครื่อง/โปรโมชัน และกะขาย รับ-ส่งเงิน (POS Config and Shift), POS รับบิลขายจากเครื่องแคชเชียร์ กล่องรับบิล/ประมวลผล/ยกเลิก/ตัดสต็อกเป็นชุด (POS Bill Inbox), POS ซิงก์ข้อมูลเครื่องแคชเชียร์ ผูกเครื่อง/ดึงส่วนต่าง/กู้คืน/รูปภาพ (POS Device Sync) และภาพรวมโค้ดที่ จอประมวลผลระบบและ POS (System Process Workbench & POS Setup)

วิธีเปิด: เมนูแต่ละรหัส

รหัส เมนู (menu key) แท็บ/ส่วนที่เห็น
1016 กำหนดค่าเริ่มต้น POS (menu_config_pos_startup) startup ทั้ง 3 ส่วน
1017 กำหนดรหัสเครื่อง POS (menu_config_pos_machine) machines ส่วนทะเบียนเครื่อง + เลขเอกสาร + สถานะซิงก์
1018 กำหนดคุณสมบัติของเครื่อง POS (menu_config_pos_screen) machines เฉพาะส่วน "คุณสมบัติเครื่อง" 5 ส่วนย่อย (isPosScreenMenu)
1019 กำหนดเงื่อนไขสะสมแต้ม (menu_pos_point_rate) loyalty
1020 กำหนดค่าเครื่องรูดบัตรเครดิต (menu_edc_config) qr เฉพาะส่วน EDC
1021 กำหนดค่าจอแสดงผล QR Code (menu_usb_qr_display_config) qr เฉพาะส่วนจอ QR
1050 ออกแบบหน้าจอขาย POS (client_design) machines เฉพาะ "สตูดิโอออกแบบหน้าจอขาย" (isClientDesignMenu, screenRegistry.tsx:1285-1292)
1051 Download ระบบเสียงพูด (menu_pos_sound_download_install) startup เฉพาะส่วนตั้งค่าเสียง
1074 รายละเอียดคูปอง (menu_coupon_list) coupons ส่วนเพิ่ม/แก้ไข + รายการ

เมนูที่ลงทะเบียนในโค้ดแต่ ไม่โผล่ในเมนู ERP เพราะโหนดแม่ menu_so_pos_sub มี tag เป็น &2& ไม่มี &13& จึงถูกตัดโดย removeByVersion (smlMenu.ts:40-69; ชื่อเมนูใน smlMenu.json): menu_coupon_generate (สร้างคูปองแบบเร็ว), menu_save_pos_receive_money (รับเงินทอนเปิดกะ), menu_save_send_money_pos (ส่งเงินปิดกะ), pos_invoice_list_pos, pos_full_invoide_list_pos (ใบกำกับภาษีเต็มรูป) และ pos_invoice_cancel_pos (ยกเลิกใบกำกับอย่างย่อ) แท็บ promotions ก็เช่นกัน ในเมนูรหัส 2015 pos_promotion_formula ใช้จอ master-detail ของ ERP แท็บโปรโมชั่นของจอนี้เปิดได้จากหน้าตั้งค่าในพื้นที่ /pos เท่านั้น (พื้นที่ทำงาน POS จอขายแคชเชียร์ (PosDemoWorkspace, เส้นทาง /pos)) กลไกเมนูดู ทะเบียนหน้าจอและโครงเมนู (Screen registry & smlMenu)

แถบปุ่มและโหมดแก้ไข (:1083-1182)

  • แถวหัว: ชื่อจอ "หน้าจอบันทึก/แก้ไขข้อมูลและควบคุมระบบขายหน้าร้าน (SML Ai POS)", ข้อความสถานะสีเขียว, ข้อความ "ซิงก์ข้อมูลล่าสุดกับ SML Ai POS แล้ว" / "บันทึกล่าสุด <เวลา>", ป้าย "โหมดดูข้อมูล" / "โหมดแก้ไข" และลิงก์ เปิดจอขายแคชเชียร์ POS (/pos)
  • โหมดดูข้อมูล มีปุ่ม แก้ไข (ต้องมี rights.canEdit), เพิ่มใหม่ (canAdd), ลบ (canDelete) และ ปิดหน้าจอ (ถ้ามี onClose) สิทธิ์จาก useScreenRights ดู การตรวจสิทธิ์เมนูของ route process (Process route rights)
  • เพิ่มใหม่ ในแท็บเครื่อง POS เติมค่าให้ฟอร์ม: รหัส POS-0<N+1>, ชื่อ "จุดแคชเชียร์หน้าร้าน #N+1", รูปแบบเลขเอกสาร ABB<N>-@YY@MM-##### (ย่อ), TAX<N>-@YY@MM-##### (เต็มรูป), CNM<N>-@YY@MM-##### (ยกเลิก), เครื่องพิมพ์ "Thermal 80mm Auto-Cut", ระดับราคา 1 (:1125-1141)
  • โหมดแก้ไข เหลือปุ่ม บันทึก กับปุ่มที่ป้ายว่า ปิดหน้าจอ แต่ทำงานแค่ setIsEditing(false) คือ "ออกจากโหมดแก้ไขโดยไม่บันทึก" ไม่ใช่ปิดแท็บ
  • ไม่มีคีย์ลัด (ไม่ใช้ ScreenHeader) สิทธิ์อ่านอย่างเดียวบันทึกไม่ได้ ขึ้น คุณไม่มีสิทธิ์ "เพิ่ม/แก้ไขข้อมูล" ในหน้าจอนี้ ... (:759-762)

แท็บ startup: กำหนดค่าเริ่มต้น POS (1016, 1051)

ข้อมูลจากตาราง posconfig มี 10 รูปแบบ (ปุ่ม "รูปแบบ 1".."รูปแบบ 10" เลือกชุดค่า pos_config_number, :1275-1296) แบ่ง 3 ส่วน (ปุ่ม "ข้ามไปยังส่วน:" เลื่อนหน้า)

  1. ข้อมูลทั่วไปและใบเสร็จรับเงิน: รหัสชุดกำหนดค่า POS, ชื่อกิจการบนใบเสร็จ, ชื่อสาขา, เลขประจำตัวผู้เสียภาษี 13 หลัก, หมายเลขเครื่อง POS สรรพากร, รหัสลูกหนี้เริ่มต้น (ลูกค้าทั่วไป Walk-in), ประเภท/อัตรา VAT, ข้อความหัว/ท้ายใบเสร็จ, ส่วนลดสมาชิกเริ่มต้น (%), ใช้งานระบบสมาชิก, เงินสดสูงสุดในลิ้นชักที่เตือนให้นำส่ง, ค่าบริการ (%), การปัดเศษเงินทอนและรูปแบบ, รูปแบบใบเสร็จ, สิทธิ์แก้ราคา/ส่วนลด/ยกเลิกบิล, แสดงรายละเอียดภาษี, แสดงรูปสินค้าตอนสแกน, บังคับบันทึกเงินทอนเปิดกะก่อนขาย (:1297-1550)
  2. บาร์โค้ดเครื่องชั่งน้ำหนักและข้อกำหนด: รหัสนำหน้า, ตำแหน่งรหัสนำหน้า/รหัสสินค้า/ราคา/น้ำหนัก (เริ่ม-สิ้นสุด), ทศนิยมราคา, รูปแบบบิลขายเชื่อ, จำนวนเงินทอนสูงสุดและสกุล, ช่วงเวลาห้ามขายแอลกอฮอล์ (:1552-1696) ดูตรรกะบาร์โค้ดที่ บาร์โค้ดสินค้า ส่วนลดบาร์โค้ด EAN13 และพิมพ์ป้าย (Barcode menus 2.1.7-2.1.17)
  3. สิทธิ์และตัวเลือกควบคุมจุดแคชเชียร์: ชุด checkbox 29 ตัว (:1704-1732) เช่น อนุญาตแก้ไขราคาขาย, ตรวจสอบการส่งเงินก่อนปิดกะ, ใช้งานสินค้าชุด, พิมพ์ใบเสร็จหลายภาษา, อนุญาตยกเลิกบิล/ข้ามวัน, ห้ามยกเลิกบิลนอกกะ, ถามรหัสผ่านก่อนเปิดลิ้นชัก, ควบคุมยอดคงเหลือติดลบ, คำนวณแต้มเฉพาะสมาชิก, ห้ามขายสินค้าที่ไม่มีราคา, บังคับเลือกประเภทบัตรเครดิต
  • เมนู 1051 (ระบบเสียงพูด) แสดงตารางตั้งค่าเสียง 6 เหตุการณ์ (:1214-1245): สแกนบาร์โค้ด, มีสินค้าในรายการแล้ว, เปิดลิ้นชัก, ไม่พบบาร์โค้ด, เลือกสมาชิก, ปิดการขาย/ขานเงินทอน พร้อมชื่อไฟล์เสียง (เช่น beep_scan.wav)

แท็บ machines: เครื่อง POS (1017, 1018, 1050)

ส่วนของ 1017 (3 ส่วนข้ามไปได้):

  1. ทะเบียนรหัสเครื่อง POS และอุปกรณ์: ตารางเครื่อง (คลิกแถวเพื่อแก้) และฟอร์ม รหัสเครื่อง, ชื่อจุดขาย, เลขทะเบียน RD Terminal ID, รหัสชุดค่า POS, คลังและที่เก็บตัดสต็อกประจำเครื่อง, ระดับราคา 1-9, รหัสแบบฟอร์มใบเสร็จ, ชื่อเครื่องพิมพ์, จอฝั่งลูกค้า, ลิ้นชักอัตโนมัติ, ประเภทการพิมพ์, สำเนาใบเสร็จอิเล็กทรอนิกส์, อนุญาตขายเชื่อ/สถานะ (:2055-2290)
  2. รูปแบบเลขที่เอกสารประจำเครื่อง: เลขที่เอกสารย่อ/เต็มรูป/ยกเลิก/รับเงินทอนเปิดกะ/ส่งเงินปิดกะ, รหัสเอกสารและเลขรัน, ขายเชื่อ, ลำดับรายงานสรุปยอดขาย, ข้อความหัวบิลประจำเครื่อง และการตั้ง KBank QR API (:2319-2440) รูปแบบเลขใช้ตัวแปร @YY@MM-##### (แบ็กเอนด์ตรวจ doc_format ซ้ำ/ไม่มี # แล้วตอบ 400 ที่จอแสดงตรง ๆ :804) หลักเลขเอกสารดู สถานะต่อเนื่องของเอกสาร กราฟโยงเอกสาร และเลขที่เอกสารถัดไป (Doc flow & numbering)
  3. สถานะซิงก์เครื่อง POS และรหัสเชื่อมเครื่อง (:1782-1935): สรุป "รอคำนวณสต็อก N รายการ", "บิลผิดพลาด N บิล", ปุ่ม ประมวลผลบิลที่ผิดพลาดใหม่ (POST /api/pos/bills/reprocess), ปุ่ม รีเฟรช และตารางเครื่อง (สถานะ, ซิงก์ล่าสุด, พบเครื่องล่าสุด, บิลรอส่ง, บิลผิดพลาด, เวอร์ชันแอป) แต่ละแถวมีปุ่ม สร้างรหัสเชื่อมเครื่อง เปิดหน้าต่างยืนยัน แล้วเรียก POST /api/pos/devices/<เครื่อง>/pair ได้รหัสที่แสดง ครั้งเดียว พร้อมปุ่ม "คัดลอกรหัส" (:1007-1037, ข้อความ "รหัสนี้แสดงครั้งเดียว") รีเฟรชอัตโนมัติเป็นช่วง ๆ (:1929)
  • เมนู 1018 (isPosScreenMenu, :2476-2778): 5 ส่วนย่อย กำหนดทั่วไปและเครื่องพิมพ์ (รหัสเครื่อง, รูปแบบ/ฟอร์มใบเสร็จ, ชนิดเครื่องพิมพ์, พอร์ตลิ้นชัก, เครื่องพิมพ์ใบกำกับเต็มรูป) / จอแสดงผล (หน้าจอหลัก, หน้าจอที่ 2, จำนวนรายการค้นหาสูงสุด) / ฟอนต์ใบเสร็จ (หัว, รายการ, ท้าย, กว้างกระดาษ px) / ระบบเสียง / จอแสดงผลลูกค้า (พอร์ต, Baud Rate, Parity, จำนวนตัวอักษรต่อบรรทัด)
  • เมนู 1050 (isClientDesignMenu, :2778-2884): "สตูดิโอออกแบบหน้าจอขาย POS และปุ่มลัดสินค้า" ตั้งรหัสผังหน้าจอขาย, ชื่อรูปแบบ, ความละเอียด, รูปแบบการจัดวาง, จำนวนคอลัมน์/แถวปุ่มสินค้าด่วน, ขนาดตัวอักษรยอดรวม, ธีมสี (ตาราง pos_screen_define, :2783)
  • ลบเครื่อง: ถามยืนยัน "มีข้อมูลที่ต้องลบจำนวน: 1 รายการ ต้องการลบ <รหัส> จริงหรือไม่" (ค่าเริ่มต้น = ไม่ลบ) แล้วรัน DELETE FROM pos_id WHERE UPPER(machinecode)=UPPER(...) ผ่าน queryExec ตรง ๆ (:826-840)

แท็บ loyalty: เงื่อนไขสะสมแต้ม (1019)

ฟอร์มกำหนด: ยอดซื้อทุกกี่บาทได้ 1 แต้ม, แต้มที่ใช้แลกส่วนลด 1 บาท, แต้มขั้นต่ำที่แลกได้, รหัสเงื่อนไข, ตัวคูณแต้มเดือนเกิดและวันเกิด, เกณฑ์ขึ้นระดับ Silver / Gold / Platinum (:3636-3860) ด้านล่างมีตารางช่วงวันที่สะสมแต้มและวันพิเศษ, กลุ่มสมาชิกสะสมแต้มร่วมกัน, และรายการลูกค้าชั่วคราวที่บันทึกตอนสาย LAN หลุด พร้อมปุ่ม reconcile เป็นสมาชิกถาวร (handleReconcileTempMember, :1055-1080) บันทึกส่ง section: "point" ไป POST /api/pos/config

แท็บ qr: QR และเครื่องรูดบัตร (1020, 1021)

  • ทั่วไป: PromptPay / Thai QR มาตรฐาน EMVCo: รหัสเครื่อง, รูปแบบสร้าง QR, ชื่อร้านค้า (Merchant Name), รหัสพร้อมเพย์ e-Wallet, Biller ID 15 หลัก, Terminal ID, Store ID (:4007-4090)
  • 1020 EDC: พอร์ตเครื่องรูดบัตร (และ KTB), รูปแบบเครื่อง, Baud Rate, Parity/Data/Stop (:4099-4180)
  • 1021 จอ QR: พอร์ต, Baud Rate, Parity/Data/Stop (:4185-4245)
  • บันทึกส่ง section: "qr"

แท็บ coupons: คูปอง (1074)

  • ฟอร์มเพิ่ม/แก้ไขรายละเอียดคูปอง (กลุ่ม, เลขที่ ฯลฯ) และรายการคูปองทั้งหมดของระบบ (:4255-4500) บันทึก section: "coupon"
  • ลบคูปอง: ถามยืนยันแล้ว DELETE FROM coupon_list WHERE UPPER(number)=UPPER(...) (:840-850)
  • สร้างคูปองแบบเร็วเป็นชุด (เมนู menu_coupon_generate, ซ่อนจากเมนูปัจจุบัน): คำนำหน้า (Prefix), จำนวนใบที่สร้าง, มูลค่าต่อใบ -> section: "coupon_batch" ได้ข้อความ "สร้างชุดคูปอง <prefix> จำนวน <N> ใบ เรียบร้อยแล้ว" (:858-877)

แท็บ promotions: สูตรโปรโมชั่น (เปิดได้จาก /pos)

ฟอร์ม: รหัสโปรโมชั่น, ชื่อที่แสดงบนจอแคชเชียร์และท้ายใบเสร็จ, รูปแบบโปรโมชั่น (DedeCashier 10 แบบ, DEDE_PROMOTION_TYPES :55), จำนวน/ยอดซื้อขั้นต่ำ, ส่วนลด (%), จำนวนแถมฟรี, กลุ่มลูกค้าที่ได้สิทธิ์, เงื่อนไขวันพิเศษ, ขอบเขตสินค้า (เลือกสินค้าหรือหมวด), ช่วง Happy Hour (:3074-3440) ตารางทะเบียนสูตรทั้งหมด (:3451) มีปุ่มเปิด/ปิดใช้งาน (section: "promotion_toggle") และลบ (promotion_delete) พร้อมยืนยันก่อนลบ บันทึกส่ง section: "promotion" (:879-967)

แท็บ shifts: รับเงินทอน / ส่งเงิน (เมนูที่ซ่อน)

  • รับเงินทอนเปิดกะ (trans_type = 1 ตาราง poscashiersettle): เครื่อง POS, รหัสแคชเชียร์, จำนวนเงินทอนรับเข้าลิ้นชัก (บาท), หมายเหตุ
  • ส่งเงินปิดกะ (trans_type = 2): เครื่อง, แคชเชียร์, เงินสดนำส่ง, ยอดสลิปบัตรเครดิต/เดบิต, ยอดโอน QR PromptPay / คูปอง, หมายเหตุ
  • บันทึกส่ง POST /api/pos/shift ได้เลขที่เอกสารกลับ ขึ้น "บันทึกรายการ <เลข> และซิงก์ไปยังจุดแคชเชียร์..." (:786-799) ตารางด้านล่างกรองรายการตามประเภท

แท็บ bills: ใบกำกับภาษี POS (เมนูที่ซ่อน)

  • ตารางบิลล่าสุด (recentBills) ต่อหัวข้อ {title} แสดงลูกค้า, วิธีชำระ, ยอด (รูปแบบเงิน 2 ตำแหน่ง ดู ตัวเลข เงิน ภาษี และปี พ.ศ. ฝั่ง frontend (numeric.ts))
  • ในเมนู pos_invoice_cancel_pos มีปุ่ม ยกเลิกบิล ต่อแถว เรียก POST /api/pos/shift ด้วย action: "cancel_bill" เหตุผลตายตัว "ยกเลิกใบกำกับภาษีอย่างย่อจากระบบ SML Ai Account" (:969-1005) แถวที่ยกเลิกแล้วขึ้นป้าย "ยกเลิกแล้ว"
  • ในเมนู pos_full_invoide_list_pos มีฟอร์ม "ออกใบกำกับภาษีเต็มรูปแทนใบกำกับภาษีอย่างย่อ" (อ้างอิงเลข ABB, ลูกค้า, เลขผู้เสียภาษี/สาขา, ที่อยู่) แต่ช่วงบรรทัดนั้น (:4708-4746) ไม่มี onChange, value หรือปุ่มบันทึกเลย จึงเป็นเพียงหน้าตา ไม่มีการออกใบกำกับจริงจากจอนี้

การโหลดและบันทึกข้อมูล

  • เปิดจอเรียก GET /api/pos/bootstrap?holding_code=DATA&branch_code=00000 ครั้งเดียว ได้ config, เครื่อง, สินค้า, เงื่อนไขแต้ม, โปรโมชั่น, QR, คูปอง, รายการรับ-ส่งเงิน, บิลล่าสุด, กลุ่มสมาชิก, ลูกค้าชั่วคราว (:488-540) ค่า holding_code และ branch_code ตายตัวในโค้ด
  • บันทึกทุกแท็บยกเว้นโปรโมชั่นและกะ: POST /api/pos/config ด้วย {section, ...ฟอร์ม} โดย section คือ startup / machine / point / qr / coupon (:770-802) แล้วโหลด bootstrap ใหม่ ขึ้น "บันทึกการกำหนดค่า POS และซิงก์ไปยังเครื่องแคชเชียร์..."
  • ข้อผิดพลาดจากเซิร์ฟเวอร์แสดงเป็นแถบแดงเหนือเนื้อหา (apiErrorMessage, :166)

ข้อควรระวัง

  • ปุ่มที่ป้ายว่า "ปิดหน้าจอ" ในโหมดแก้ไขแค่ยกเลิกการแก้ ไม่ปิดแท็บ
  • ค่า holding_code=DATA / branch_code=00000 ตายตัว หลายสาขาจึงยังไม่แยกที่จอนี้
  • เมนูรับ-ส่งเงิน, คูปองแบบเร็ว, รายการใบกำกับ POS ถูกซ่อนจากเมนู ERP ที่ tag &13& (ดูด้านบน) เข้าได้เฉพาะทางโค้ดหรือเมื่อ tag ถูกเปลี่ยน
  • ตารางที่แตะ: posconfig, pos_id, coupon_list, poscashiersettle, pos_screen_define (ยังไม่มีบันทึกตารางในคลัง ดูภาพรวมที่ ภาพรวมพจนานุกรมข้อมูล: ตารางฐานข้อมูล (tables overview))

ที่มาในโค้ด