mirror of
https://github.com/opensourcepos/opensourcepos.git
synced 2026-06-07 15:14:25 -04:00
Compare commits
33 Commits
issue-4459
...
bootstrap-
| Author | SHA1 | Date | |
|---|---|---|---|
|
|
61a69a1ff9 | ||
|
|
e081de8e7d | ||
|
|
9509a97164 | ||
|
|
5450404cb2 | ||
|
|
b7384296c1 | ||
|
|
b0dddc22a3 | ||
|
|
8d6b166673 | ||
|
|
093ec7fb13 | ||
|
|
9c89a2e2cb | ||
|
|
2f51c4ef52 | ||
|
|
def0c27a0e | ||
|
|
90c981b6b7 | ||
|
|
6ff28d8a4d | ||
|
|
70fb347fc4 | ||
|
|
2f5c0130f4 | ||
|
|
fdd6a408ec | ||
|
|
ef91e6a9df | ||
|
|
144e73eba6 | ||
|
|
42ba39d290 | ||
|
|
81213f0434 | ||
|
|
7edefe8ee1 | ||
|
|
68e14191f9 | ||
|
|
a381c3ca54 | ||
|
|
058e12244e | ||
|
|
f1c6fe2981 | ||
|
|
ff7a8d2e88 | ||
|
|
e602eddb47 | ||
|
|
0a313aa09d | ||
|
|
12e3c7e31f | ||
|
|
de62e9f3bd | ||
|
|
97ca738b2d | ||
|
|
c714dd6f68 | ||
|
|
b6f28da058 |
@@ -16,6 +16,9 @@ CI_ENVIRONMENT = production
|
|||||||
# Configure with comma-separated list of domains/subdomains:
|
# Configure with comma-separated list of domains/subdomains:
|
||||||
# app.allowedHostnames = 'yourdomain.com,www.yourdomain.com'
|
# app.allowedHostnames = 'yourdomain.com,www.yourdomain.com'
|
||||||
#
|
#
|
||||||
|
# Or via environment variable (useful for Docker/Compose):
|
||||||
|
# ALLOWED_HOSTNAMES=yourdomain.com,www.yourdomain.com
|
||||||
|
#
|
||||||
# For local development:
|
# For local development:
|
||||||
# app.allowedHostnames = 'localhost'
|
# app.allowedHostnames = 'localhost'
|
||||||
#
|
#
|
||||||
|
|||||||
1
.github/workflows/build-release.yml
vendored
1
.github/workflows/build-release.yml
vendored
@@ -123,6 +123,7 @@ jobs:
|
|||||||
.
|
.
|
||||||
!.git
|
!.git
|
||||||
!node_modules
|
!node_modules
|
||||||
|
include-hidden-files: true
|
||||||
retention-days: 1
|
retention-days: 1
|
||||||
|
|
||||||
docker:
|
docker:
|
||||||
|
|||||||
219
.github/workflows/deploy-core.yml
vendored
Normal file
219
.github/workflows/deploy-core.yml
vendored
Normal file
@@ -0,0 +1,219 @@
|
|||||||
|
name: Deploy Core
|
||||||
|
|
||||||
|
on:
|
||||||
|
workflow_call:
|
||||||
|
inputs:
|
||||||
|
image_tag:
|
||||||
|
description: 'Docker image tag to deploy'
|
||||||
|
type: string
|
||||||
|
required: true
|
||||||
|
sha:
|
||||||
|
description: 'Git commit SHA to deploy'
|
||||||
|
type: string
|
||||||
|
required: true
|
||||||
|
description:
|
||||||
|
description: 'Deployment description'
|
||||||
|
type: string
|
||||||
|
required: true
|
||||||
|
pr_number:
|
||||||
|
description: 'Pull request number (optional)'
|
||||||
|
type: string
|
||||||
|
required: false
|
||||||
|
outputs:
|
||||||
|
deployment_id:
|
||||||
|
description: 'GitHub deployment ID'
|
||||||
|
value: ${{ jobs.deploy.outputs.deployment_id }}
|
||||||
|
status:
|
||||||
|
description: 'Deployment status (success/failure)'
|
||||||
|
value: ${{ jobs.deploy.outputs.status }}
|
||||||
|
|
||||||
|
concurrency:
|
||||||
|
group: deploy-staging
|
||||||
|
cancel-in-progress: false
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
contents: read
|
||||||
|
deployments: write
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
deploy:
|
||||||
|
name: Deploy to staging
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
|
||||||
|
environment:
|
||||||
|
name: staging
|
||||||
|
url: ${{ vars.DEPLOY_URL || 'https://dev.opensourcepos.org' }}
|
||||||
|
deployment: false
|
||||||
|
|
||||||
|
outputs:
|
||||||
|
deployment_id: ${{ steps.deployment.outputs.deployment_id }}
|
||||||
|
status: ${{ steps.webhook.outputs.status }}
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- name: Create GitHub Deployment
|
||||||
|
id: deployment
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ github.token }}
|
||||||
|
IMAGE_TAG: ${{ inputs.image_tag }}
|
||||||
|
REF_SHA: ${{ inputs.sha }}
|
||||||
|
DESCRIPTION: ${{ inputs.description }}
|
||||||
|
run: |
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
DEPLOYMENT_ID=$(gh api "repos/${GITHUB_REPOSITORY}/deployments" \
|
||||||
|
-X POST \
|
||||||
|
-f ref="${REF_SHA}" \
|
||||||
|
-f environment="staging" \
|
||||||
|
-f description="${DESCRIPTION}" \
|
||||||
|
-F auto_merge=false \
|
||||||
|
-F required_contexts[] \
|
||||||
|
--jq '.id')
|
||||||
|
|
||||||
|
if [ -z "$DEPLOYMENT_ID" ]; then
|
||||||
|
echo "::error::Failed to create deployment"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "deployment_id=$DEPLOYMENT_ID" >> "$GITHUB_OUTPUT"
|
||||||
|
echo "Created deployment: $DEPLOYMENT_ID"
|
||||||
|
|
||||||
|
- name: Set deployment status to in_progress
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ github.token }}
|
||||||
|
run: |
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
gh api "repos/${GITHUB_REPOSITORY}/deployments/${{ steps.deployment.outputs.deployment_id }}/statuses" \
|
||||||
|
-X POST \
|
||||||
|
-f state="in_progress" \
|
||||||
|
-f description="Deployment in progress..." \
|
||||||
|
-f log_url="${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}"
|
||||||
|
|
||||||
|
- name: Trigger deployment webhook
|
||||||
|
id: webhook
|
||||||
|
env:
|
||||||
|
DEPLOY_WEBHOOK_URL: ${{ secrets.DEPLOY_WEBHOOK_URL }}
|
||||||
|
DEPLOY_WEBHOOK_SECRET: ${{ secrets.DEPLOY_WEBHOOK_SECRET }}
|
||||||
|
DOCKER_REPO_NAME: ${{ secrets.DOCKER_REPO_NAME }}
|
||||||
|
IMAGE_TAG: ${{ inputs.image_tag }}
|
||||||
|
REF_SHA: ${{ inputs.sha }}
|
||||||
|
DEPLOYMENT_ID: ${{ steps.deployment.outputs.deployment_id }}
|
||||||
|
PR_NUMBER: ${{ inputs.pr_number }}
|
||||||
|
run: |
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
if [ -z "$DEPLOY_WEBHOOK_URL" ]; then
|
||||||
|
echo "::error::DEPLOY_WEBHOOK_URL secret is not configured"
|
||||||
|
echo "Please add the DEPLOY_WEBHOOK_URL secret in your repository settings"
|
||||||
|
echo "status=failure" >> "$GITHUB_OUTPUT"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
|
|
||||||
|
REPO_NAME="${DOCKER_REPO_NAME:-opensourcepos/opensourcepos}"
|
||||||
|
REPO_NAMESPACE="${REPO_NAME%%/*}"
|
||||||
|
REPO_SHORT_NAME="${REPO_NAME#*/}"
|
||||||
|
PUSHED_AT=$(date +%s)
|
||||||
|
|
||||||
|
if [ -n "$PR_NUMBER" ]; then
|
||||||
|
PAYLOAD=$(jq -n \
|
||||||
|
--arg callback_url "${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" \
|
||||||
|
--argjson pushed_at "$PUSHED_AT" \
|
||||||
|
--arg pusher "$GITHUB_ACTOR" \
|
||||||
|
--arg tag "$IMAGE_TAG" \
|
||||||
|
--arg repo_name "$REPO_NAME" \
|
||||||
|
--arg name "$REPO_SHORT_NAME" \
|
||||||
|
--arg namespace "$REPO_NAMESPACE" \
|
||||||
|
--arg repo_url "https://hub.docker.com/r/${REPO_NAME}/" \
|
||||||
|
--arg deployment_id "$DEPLOYMENT_ID" \
|
||||||
|
--arg repository "$GITHUB_REPOSITORY" \
|
||||||
|
--arg sha "$REF_SHA" \
|
||||||
|
--arg run_id "$GITHUB_RUN_ID" \
|
||||||
|
--arg actor "$GITHUB_ACTOR" \
|
||||||
|
--argjson pr_number "$PR_NUMBER" \
|
||||||
|
'{
|
||||||
|
callback_url: $callback_url,
|
||||||
|
push_data: {pushed_at: $pushed_at, pusher: $pusher, tag: $tag},
|
||||||
|
repository: {repo_name: $repo_name, name: $name, namespace: $namespace, repo_url: $repo_url, status: "Active"},
|
||||||
|
github_deployment: {id: $deployment_id, environment: "staging", repository: $repository, sha: $sha, run_id: $run_id, actor: $actor, pull_request: $pr_number}
|
||||||
|
}')
|
||||||
|
else
|
||||||
|
PAYLOAD=$(jq -n \
|
||||||
|
--arg callback_url "${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" \
|
||||||
|
--argjson pushed_at "$PUSHED_AT" \
|
||||||
|
--arg pusher "$GITHUB_ACTOR" \
|
||||||
|
--arg tag "$IMAGE_TAG" \
|
||||||
|
--arg repo_name "$REPO_NAME" \
|
||||||
|
--arg name "$REPO_SHORT_NAME" \
|
||||||
|
--arg namespace "$REPO_NAMESPACE" \
|
||||||
|
--arg repo_url "https://hub.docker.com/r/${REPO_NAME}/" \
|
||||||
|
--arg deployment_id "$DEPLOYMENT_ID" \
|
||||||
|
--arg repository "$GITHUB_REPOSITORY" \
|
||||||
|
--arg sha "$REF_SHA" \
|
||||||
|
--arg run_id "$GITHUB_RUN_ID" \
|
||||||
|
--arg actor "$GITHUB_ACTOR" \
|
||||||
|
'{
|
||||||
|
callback_url: $callback_url,
|
||||||
|
push_data: {pushed_at: $pushed_at, pusher: $pusher, tag: $tag},
|
||||||
|
repository: {repo_name: $repo_name, name: $name, namespace: $namespace, repo_url: $repo_url, status: "Active"},
|
||||||
|
github_deployment: {id: $deployment_id, environment: "staging", repository: $repository, sha: $sha, run_id: $run_id, actor: $actor}
|
||||||
|
}')
|
||||||
|
fi
|
||||||
|
|
||||||
|
echo "Sending webhook..."
|
||||||
|
echo "Image: ${IMAGE_TAG}"
|
||||||
|
echo "Environment: staging"
|
||||||
|
|
||||||
|
HEADERS=(-H "Content-Type: application/json")
|
||||||
|
|
||||||
|
if [ -n "$DEPLOY_WEBHOOK_SECRET" ]; then
|
||||||
|
SIGNATURE=$(printf '%s' "$PAYLOAD" | openssl dgst -sha256 -hmac "$DEPLOY_WEBHOOK_SECRET" | sed 's/.*= //')
|
||||||
|
HEADERS+=(-H "X-Hub-Signature-256: sha256=$SIGNATURE")
|
||||||
|
echo "Using HMAC-SHA256 signature verification"
|
||||||
|
else
|
||||||
|
echo "::warning::DEPLOY_WEBHOOK_SECRET not set - webhook calls will not be signed"
|
||||||
|
echo "For security, configure DEPLOY_WEBHOOK_SECRET in your repository settings"
|
||||||
|
fi
|
||||||
|
|
||||||
|
HTTP_CODE=$(curl -sS --connect-timeout 10 --max-time 120 \
|
||||||
|
-o response.txt -w "%{http_code}" \
|
||||||
|
-X POST \
|
||||||
|
"${HEADERS[@]}" \
|
||||||
|
-d "$PAYLOAD" \
|
||||||
|
"$DEPLOY_WEBHOOK_URL") || HTTP_CODE="000"
|
||||||
|
|
||||||
|
echo "Response code: $HTTP_CODE"
|
||||||
|
if [ -s response.txt ]; then
|
||||||
|
cat response.txt
|
||||||
|
fi
|
||||||
|
|
||||||
|
if [ "$HTTP_CODE" -ge 200 ] && [ "$HTTP_CODE" -lt 300 ]; then
|
||||||
|
echo "status=success" >> "$GITHUB_OUTPUT"
|
||||||
|
else
|
||||||
|
echo "status=failure" >> "$GITHUB_OUTPUT"
|
||||||
|
fi
|
||||||
|
|
||||||
|
- name: Set deployment status
|
||||||
|
if: always()
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ github.token }}
|
||||||
|
IMAGE_TAG: ${{ inputs.image_tag }}
|
||||||
|
run: |
|
||||||
|
set -euo pipefail
|
||||||
|
|
||||||
|
STATE="${{ steps.webhook.outputs.status }}"
|
||||||
|
|
||||||
|
if [ "$STATE" = "success" ]; then
|
||||||
|
DESCRIPTION=$(jq -nr --arg tag "$IMAGE_TAG" \
|
||||||
|
'"Deployed image \($tag) to staging"')
|
||||||
|
|
||||||
|
gh api "repos/${GITHUB_REPOSITORY}/deployments/${{ steps.deployment.outputs.deployment_id }}/statuses" \
|
||||||
|
-X POST \
|
||||||
|
-f state="success" \
|
||||||
|
-f description="$DESCRIPTION"
|
||||||
|
else
|
||||||
|
gh api "repos/${GITHUB_REPOSITORY}/deployments/${{ steps.deployment.outputs.deployment_id }}/statuses" \
|
||||||
|
-X POST \
|
||||||
|
-f state="failure" \
|
||||||
|
-f description="Deployment failed"
|
||||||
|
exit 1
|
||||||
|
fi
|
||||||
79
.github/workflows/deploy-pr.yml
vendored
Normal file
79
.github/workflows/deploy-pr.yml
vendored
Normal file
@@ -0,0 +1,79 @@
|
|||||||
|
name: PR Deploy
|
||||||
|
|
||||||
|
on:
|
||||||
|
pull_request_review:
|
||||||
|
types: [submitted]
|
||||||
|
|
||||||
|
concurrency:
|
||||||
|
group: staging-deploy
|
||||||
|
cancel-in-progress: false
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
contents: read
|
||||||
|
deployments: write
|
||||||
|
pull-requests: write
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
prepare:
|
||||||
|
name: Prepare deployment
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
if: >
|
||||||
|
github.event.review.state == 'approved' &&
|
||||||
|
github.event.pull_request.head.repo.full_name == github.repository
|
||||||
|
outputs:
|
||||||
|
image_tag: ${{ steps.image.outputs.tag }}
|
||||||
|
sha: ${{ github.event.pull_request.head.sha }}
|
||||||
|
pr_number: ${{ github.event.pull_request.number }}
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- name: Checkout PR
|
||||||
|
uses: actions/checkout@v4
|
||||||
|
with:
|
||||||
|
ref: ${{ github.event.pull_request.head.sha }}
|
||||||
|
|
||||||
|
- name: Get image tag
|
||||||
|
id: image
|
||||||
|
env:
|
||||||
|
PR_NUMBER: ${{ github.event.pull_request.number }}
|
||||||
|
PR_SHA: ${{ github.event.pull_request.head.sha }}
|
||||||
|
run: |
|
||||||
|
IMAGE_TAG="pr-${PR_NUMBER}-${PR_SHA:0:7}"
|
||||||
|
echo "tag=$IMAGE_TAG" >> "$GITHUB_OUTPUT"
|
||||||
|
|
||||||
|
deploy:
|
||||||
|
name: Deploy to staging
|
||||||
|
needs: prepare
|
||||||
|
uses: ./.github/workflows/deploy-core.yml
|
||||||
|
with:
|
||||||
|
image_tag: ${{ needs.prepare.outputs.image_tag }}
|
||||||
|
sha: ${{ needs.prepare.outputs.sha }}
|
||||||
|
description: Deploy PR #${{ needs.prepare.outputs.pr_number }} to staging
|
||||||
|
pr_number: ${{ needs.prepare.outputs.pr_number }}
|
||||||
|
secrets: inherit
|
||||||
|
|
||||||
|
comment:
|
||||||
|
name: Comment deployment status
|
||||||
|
needs: [prepare, deploy]
|
||||||
|
if: always()
|
||||||
|
runs-on: ubuntu-latest
|
||||||
|
env:
|
||||||
|
GH_TOKEN: ${{ github.token }}
|
||||||
|
IMAGE_TAG: ${{ needs.prepare.outputs.image_tag }}
|
||||||
|
PR_NUMBER: ${{ needs.prepare.outputs.pr_number }}
|
||||||
|
REF_SHA: ${{ needs.prepare.outputs.sha }}
|
||||||
|
STATUS: ${{ needs.deploy.outputs.status }}
|
||||||
|
|
||||||
|
steps:
|
||||||
|
- name: Comment on PR
|
||||||
|
run: |
|
||||||
|
if [ "$STATUS" = "success" ]; then
|
||||||
|
BODY=$(jq -nr --arg tag "$IMAGE_TAG" --arg sha "$REF_SHA" --arg url "${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" \
|
||||||
|
'"✅ **Staging deployment completed**\n\n🔗 **URL**: https://dev.opensourcepos.org\n📦 **Image Tag**: `\($tag)`\n🔨 **Commit**: \($sha)\n\nView logs: \($url)"')
|
||||||
|
else
|
||||||
|
BODY=$(jq -nr --arg url "${GITHUB_SERVER_URL}/${GITHUB_REPOSITORY}/actions/runs/${GITHUB_RUN_ID}" \
|
||||||
|
'"❌ **Staging deployment failed**\n\nCheck the [workflow logs](\($url)) for details."')
|
||||||
|
fi
|
||||||
|
|
||||||
|
gh api "repos/${GITHUB_REPOSITORY}/issues/${PR_NUMBER}/comments" \
|
||||||
|
-X POST \
|
||||||
|
-f body="$BODY"
|
||||||
23
.github/workflows/deploy.yml
vendored
Normal file
23
.github/workflows/deploy.yml
vendored
Normal file
@@ -0,0 +1,23 @@
|
|||||||
|
name: Deploy
|
||||||
|
|
||||||
|
on:
|
||||||
|
workflow_dispatch:
|
||||||
|
inputs:
|
||||||
|
image_tag:
|
||||||
|
description: 'Docker image tag to deploy (e.g., v3.4.0, latest)'
|
||||||
|
required: true
|
||||||
|
default: 'latest'
|
||||||
|
|
||||||
|
permissions:
|
||||||
|
contents: read
|
||||||
|
deployments: write
|
||||||
|
|
||||||
|
jobs:
|
||||||
|
deploy:
|
||||||
|
name: Deploy to staging
|
||||||
|
uses: ./.github/workflows/deploy-core.yml
|
||||||
|
with:
|
||||||
|
image_tag: ${{ inputs.image_tag }}
|
||||||
|
sha: ${{ github.sha }}
|
||||||
|
description: Deploy image ${{ inputs.image_tag }}
|
||||||
|
secrets: inherit
|
||||||
33
CHANGELOG.md
33
CHANGELOG.md
@@ -1,5 +1,4 @@
|
|||||||
[unreleased]: https://github.com/opensourcepos/opensourcepos/compare/3.4.0...HEAD
|
[unreleased]: https://github.com/opensourcepos/opensourcepos/compare/3.4.1...HEAD
|
||||||
[3.4.2]: https://github.com/opensourcepos/opensourcepos/compare/3.4.1...3.4.2
|
|
||||||
[3.4.1]: https://github.com/opensourcepos/opensourcepos/compare/3.4.0...3.4.1
|
[3.4.1]: https://github.com/opensourcepos/opensourcepos/compare/3.4.0...3.4.1
|
||||||
[3.4.0]: https://github.com/opensourcepos/opensourcepos/compare/3.3.9...3.4.0
|
[3.4.0]: https://github.com/opensourcepos/opensourcepos/compare/3.3.9...3.4.0
|
||||||
[3.3.9]: https://github.com/opensourcepos/opensourcepos/compare/3.3.8...3.3.9
|
[3.3.9]: https://github.com/opensourcepos/opensourcepos/compare/3.3.8...3.3.9
|
||||||
@@ -34,10 +33,36 @@ All notable changes to this project will be documented in this file.
|
|||||||
|
|
||||||
## [Unreleased]
|
## [Unreleased]
|
||||||
|
|
||||||
## [3.4.0] - 2025-02-06
|
## [3.4.1] - 2025-06-05
|
||||||
|
- Feature: PSR-12 Compliant Indentation by @objecttothis in ([#4196](https://github.com/opensourcepos/opensourcepos/pull/4196))
|
||||||
|
- Add .env to dist zip by @jekkos in ([#4199](https://github.com/opensourcepos/opensourcepos/pull/4199))
|
||||||
|
- Add CI4 coding standards linter ([#3708](https://github.com/opensourcepos/opensourcepos/issues/3708)) by @jekkos in ([#4198](https://github.com/opensourcepos/opensourcepos/pull/4198))
|
||||||
|
- Bump canvg from 3.0.10 to 3.0.11 by @dependabot in ([#4189](https://github.com/opensourcepos/opensourcepos/pull/4189))
|
||||||
|
- Bump jspdf and jspdf-autotable by @dependabot in ([#4190](https://github.com/opensourcepos/opensourcepos/pull/4190))
|
||||||
|
- Feature bump ci to 4.6.0 by @objecttothis in ([#4197](https://github.com/opensourcepos/opensourcepos/pull/4197))
|
||||||
|
- Add Kurdish language option to UI by @BudsieBuds in ([#4210](https://github.com/opensourcepos/opensourcepos/pull/4210))
|
||||||
|
- Convert language ku to ckb by @BudsieBuds in ([#4211](https://github.com/opensourcepos/opensourcepos/pull/4211))
|
||||||
|
- Fix PHP 8.4 errors by @BudsieBuds in ([#4215](https://github.com/opensourcepos/opensourcepos/pull/4215))
|
||||||
|
- Add default bootstrap to themes by @BudsieBuds in ([#4219](https://github.com/opensourcepos/opensourcepos/pull/4219))
|
||||||
|
- Update language names by @BudsieBuds in ([#4218](https://github.com/opensourcepos/opensourcepos/pull/4218))
|
||||||
|
- Update install docs by @BudsieBuds in ([#4217](https://github.com/opensourcepos/opensourcepos/pull/4217))
|
||||||
|
- Convert menu icons to SVG by @BudsieBuds in ([#4220](https://github.com/opensourcepos/opensourcepos/pull/4220))
|
||||||
|
- Enhance license handling by @BudsieBuds in ([#4223](https://github.com/opensourcepos/opensourcepos/pull/4223))
|
||||||
|
- Fix datetime rendering ([#4226](https://github.com/opensourcepos/opensourcepos/issues/4226)) by @jekkos in ([#4227](https://github.com/opensourcepos/opensourcepos/pull/4227))
|
||||||
|
- Fix datetime rendering by @jekkos in ([#4228](https://github.com/opensourcepos/opensourcepos/pull/4228))
|
||||||
|
- Fix null error when sending by email a receipt of a sale that has no invoice by @diego-ramos in ([#4229](https://github.com/opensourcepos/opensourcepos/pull/4229))
|
||||||
|
- Update Receivings.php to save form. by @odiea in ([#4231](https://github.com/opensourcepos/opensourcepos/pull/4231))
|
||||||
|
- Update Cashups.php for ajax cashup total to work. by @odiea in ([#4238](https://github.com/opensourcepos/opensourcepos/pull/4238))
|
||||||
|
- Coding style updates for PSR-12 compliance & improved readability by @BudsieBuds in ([#4204](https://github.com/opensourcepos/opensourcepos/pull/4204))
|
||||||
|
- Fix Codeigniter disallowed characters error with payment types that have accents by @diego-ramos in ([#4232](https://github.com/opensourcepos/opensourcepos/pull/4232))
|
||||||
|
- Fixed broken escape string for success & warning messages by @Franchovy in ([#4253](https://github.com/opensourcepos/opensourcepos/pull/4253))
|
||||||
|
- Bugfix constraint migration fix by @objecttothis in ([#4230](https://github.com/opensourcepos/opensourcepos/pull/4230))
|
||||||
|
- Fix item number lookup in sales/receivings ([#4212](https://github.com/opensourcepos/opensourcepos/issues/4212)) by @jekkos in ([#4250](https://github.com/opensourcepos/opensourcepos/pull/4250))
|
||||||
|
|
||||||
|
## [3.4.0] - 2025-03-23
|
||||||
|
|
||||||
- Translation updates (Spanish, Indonesian, Swedish, Urdu, Chinese, Thai, French, Dutch)
|
- Translation updates (Spanish, Indonesian, Swedish, Urdu, Chinese, Thai, French, Dutch)
|
||||||
- PHP 8.x support
|
- PHP `8.x` support
|
||||||
- Security fixes (XSS, SQLi)
|
- Security fixes (XSS, SQLi)
|
||||||
- Migration to Gulp as buildsystem
|
- Migration to Gulp as buildsystem
|
||||||
- Decimal validation fix
|
- Decimal validation fix
|
||||||
|
|||||||
@@ -1,98 +1,85 @@
|
|||||||
Contributor Covenant Code of Conduct
|
[comment]: # (Contributor Covenant 2.1 - from https://www.contributor-covenant.org/version/2/1/code_of_conduct/code_of_conduct.md)
|
||||||
Our Pledge
|
|
||||||
We as members, contributors, and leaders pledge to make participation in our
|
# Contributor Covenant Code of Conduct
|
||||||
community a harassment-free experience for everyone, regardless of age, body
|
|
||||||
size, visible or invisible disability, ethnicity, sex characteristics, gender
|
## Our Pledge
|
||||||
identity and expression, level of experience, education, socio-economic status,
|
|
||||||
nationality, personal appearance, race, caste, color, religion, or sexual
|
We as members, contributors, and leaders pledge to make participation in our community a harassment-free experience for everyone, regardless of age, body size, visible or invisible disability, ethnicity, sex characteristics, gender identity and expression, level of experience, education, socio-economic status, nationality, personal appearance, race, caste, color, religion, or sexual identity and orientation.
|
||||||
identity and orientation.
|
|
||||||
We pledge to act and interact in ways that contribute to an open, welcoming,
|
We pledge to act and interact in ways that contribute to an open, welcoming, diverse, inclusive, and healthy community.
|
||||||
diverse, inclusive, and healthy community.
|
|
||||||
Our Standards
|
## Our Standards
|
||||||
Examples of behavior that contributes to a positive environment for our
|
|
||||||
community include:
|
Examples of behavior that contributes to a positive environment for our community include:
|
||||||
|
|
||||||
* Demonstrating empathy and kindness toward other people
|
* Demonstrating empathy and kindness toward other people
|
||||||
* Being respectful of differing opinions, viewpoints, and experiences
|
* Being respectful of differing opinions, viewpoints, and experiences
|
||||||
* Giving and gracefully accepting constructive feedback
|
* Giving and gracefully accepting constructive feedback
|
||||||
* Accepting responsibility and apologizing to those affected by our mistakes,
|
* Accepting responsibility and apologizing to those affected by our mistakes, and learning from the experience
|
||||||
and learning from the experience
|
* Focusing on what is best not just for us as individuals, but for the overall community
|
||||||
* Focusing on what is best not just for us as individuals, but for the overall
|
|
||||||
community
|
|
||||||
|
|
||||||
Examples of unacceptable behavior include:
|
Examples of unacceptable behavior include:
|
||||||
|
|
||||||
* The use of sexualized language or imagery, and sexual attention or advances of
|
* The use of sexualized language or imagery, and sexual attention or advances of any kind
|
||||||
any kind
|
|
||||||
* Trolling, insulting or derogatory comments, and personal or political attacks
|
* Trolling, insulting or derogatory comments, and personal or political attacks
|
||||||
* Public or private harassment
|
* Public or private harassment
|
||||||
* Publishing others’ private information, such as a physical or email address,
|
* Publishing others' private information, such as a physical or email address, without their explicit permission
|
||||||
without their explicit permission
|
* Other conduct which could reasonably be considered inappropriate in a professional setting
|
||||||
* Other conduct which could reasonably be considered inappropriate in a
|
|
||||||
professional setting
|
|
||||||
|
|
||||||
Enforcement Responsibilities
|
## Enforcement Responsibilities
|
||||||
Community leaders are responsible for clarifying and enforcing our standards of
|
|
||||||
acceptable behavior and will take appropriate and fair corrective action in
|
|
||||||
response to any behavior that they deem inappropriate, threatening, offensive,
|
|
||||||
or harmful.
|
|
||||||
Community leaders have the right and responsibility to remove, edit, or reject
|
|
||||||
comments, commits, code, wiki edits, issues, and other contributions that are
|
|
||||||
not aligned to this Code of Conduct, and will communicate reasons for moderation
|
|
||||||
decisions when appropriate.
|
|
||||||
Scope
|
|
||||||
This Code of Conduct applies within all community spaces, and also applies when
|
|
||||||
an individual is officially representing the community in public spaces.
|
|
||||||
Examples of representing our community include using an official email address,
|
|
||||||
posting via an official social media account, or acting as an appointed
|
|
||||||
representative at an online or offline event.
|
|
||||||
Enforcement
|
|
||||||
Instances of abusive, harassing, or otherwise unacceptable behavior may be
|
|
||||||
reported to the community leaders responsible for enforcement at
|
|
||||||
[INSERT CONTACT METHOD].
|
|
||||||
All complaints will be reviewed and investigated promptly and fairly.
|
|
||||||
All community leaders are obligated to respect the privacy and security of the
|
|
||||||
reporter of any incident.
|
|
||||||
Enforcement Guidelines
|
|
||||||
Community leaders will follow these Community Impact Guidelines in determining
|
|
||||||
the consequences for any action they deem in violation of this Code of Conduct:
|
|
||||||
1. Correction
|
|
||||||
Community Impact: Use of inappropriate language or other behavior deemed
|
|
||||||
unprofessional or unwelcome in the community.
|
|
||||||
Consequence: A private, written warning from community leaders, providing
|
|
||||||
clarity around the nature of the violation and an explanation of why the
|
|
||||||
behavior was inappropriate. A public apology may be requested.
|
|
||||||
2. Warning
|
|
||||||
Community Impact: A violation through a single incident or series of
|
|
||||||
actions.
|
|
||||||
Consequence: A warning with consequences for continued behavior. No
|
|
||||||
interaction with the people involved, including unsolicited interaction with
|
|
||||||
those enforcing the Code of Conduct, for a specified period of time. This
|
|
||||||
includes avoiding interactions in community spaces as well as external channels
|
|
||||||
like social media. Violating these terms may lead to a temporary or permanent
|
|
||||||
ban.
|
|
||||||
3. Temporary Ban
|
|
||||||
Community Impact: A serious violation of community standards, including
|
|
||||||
sustained inappropriate behavior.
|
|
||||||
Consequence: A temporary ban from any sort of interaction or public
|
|
||||||
communication with the community for a specified period of time. No public or
|
|
||||||
private interaction with the people involved, including unsolicited interaction
|
|
||||||
with those enforcing the Code of Conduct, is allowed during this period.
|
|
||||||
Violating these terms may lead to a permanent ban.
|
|
||||||
4. Permanent Ban
|
|
||||||
Community Impact: Demonstrating a pattern of violation of community
|
|
||||||
standards, including sustained inappropriate behavior, harassment of an
|
|
||||||
individual, or aggression toward or disparagement of classes of individuals.
|
|
||||||
Consequence: A permanent ban from any sort of public interaction within the
|
|
||||||
community.
|
|
||||||
Attribution
|
|
||||||
This Code of Conduct is adapted from the Contributor Covenant,
|
|
||||||
version 2.1, available at
|
|
||||||
https://www.contributor-covenant.org/version/2/1/code_of_conduct.html.
|
|
||||||
Community Impact Guidelines were inspired by
|
|
||||||
Mozilla’s code of conduct enforcement ladder.
|
|
||||||
For answers to common questions about this code of conduct, see the FAQ at
|
|
||||||
https://www.contributor-covenant.org/faq. Translations are available at
|
|
||||||
https://www.contributor-covenant.org/translations.
|
|
||||||
|
|
||||||
|
Community leaders are responsible for clarifying and enforcing our standards of acceptable behavior and will take appropriate and fair corrective action in response to any behavior that they deem inappropriate, threatening, offensive, or harmful.
|
||||||
|
|
||||||
|
Community leaders have the right and responsibility to remove, edit, or reject comments, commits, code, wiki edits, issues, and other contributions that are not aligned to this Code of Conduct, and will communicate reasons for moderation decisions when appropriate.
|
||||||
|
|
||||||
|
## Scope
|
||||||
|
|
||||||
|
This Code of Conduct applies within all community spaces, and also applies when an individual is officially representing the community in public spaces. Examples of representing our community include using an official e-mail address, posting via an official social media account, or acting as an appointed representative at an online or offline event.
|
||||||
|
|
||||||
|
## Enforcement
|
||||||
|
|
||||||
|
Instances of abusive, harassing, or otherwise unacceptable behavior may be reported to the community leaders responsible for enforcement at [INSERT CONTACT METHOD]. All complaints will be reviewed and investigated promptly and fairly.
|
||||||
|
|
||||||
|
All community leaders are obligated to respect the privacy and security of the reporter of any incident.
|
||||||
|
|
||||||
|
## Enforcement Guidelines
|
||||||
|
|
||||||
|
Community leaders will follow these Community Impact Guidelines in determining the consequences for any action they deem in violation of this Code of Conduct:
|
||||||
|
|
||||||
|
### 1. Correction
|
||||||
|
|
||||||
|
**Community Impact**: Use of inappropriate language or other behavior deemed unprofessional or unwelcome in the community.
|
||||||
|
|
||||||
|
**Consequence**: A private, written warning from community leaders, providing clarity around the nature of the violation and an explanation of why the behavior was inappropriate. A public apology may be requested.
|
||||||
|
|
||||||
|
### 2. Warning
|
||||||
|
|
||||||
|
**Community Impact**: A violation through a single incident or series of actions.
|
||||||
|
|
||||||
|
**Consequence**: A warning with consequences for continued behavior. No interaction with the people involved, including unsolicited interaction with those enforcing the Code of Conduct, for a specified period of time. This includes avoiding interactions in community spaces as well as external channels like social media. Violating these terms may lead to a temporary or permanent ban.
|
||||||
|
|
||||||
|
### 3. Temporary Ban
|
||||||
|
|
||||||
|
**Community Impact**: A serious violation of community standards, including sustained inappropriate behavior.
|
||||||
|
|
||||||
|
**Consequence**: A temporary ban from any sort of interaction or public communication with the community for a specified period of time. No public or private interaction with the people involved, including unsolicited interaction with those enforcing the Code of Conduct, is allowed during this period. Violating these terms may lead to a permanent ban.
|
||||||
|
|
||||||
|
### 4. Permanent Ban
|
||||||
|
|
||||||
|
**Community Impact**: Demonstrating a pattern of violation of community standards, including sustained inappropriate behavior, harassment of an individual, or aggression toward or disparagement of classes of individuals.
|
||||||
|
|
||||||
|
**Consequence**: A permanent ban from any sort of public interaction within the community.
|
||||||
|
|
||||||
|
## Attribution
|
||||||
|
|
||||||
|
This Code of Conduct is adapted from the [Contributor Covenant][homepage], version 2.1, available at [https://www.contributor-covenant.org/version/2/1/code_of_conduct.html][v2.1].
|
||||||
|
|
||||||
|
Community Impact Guidelines were inspired by [Mozilla's code of conduct enforcement ladder][Mozilla CoC].
|
||||||
|
|
||||||
|
For answers to common questions about this code of conduct, see the FAQ at [https://www.contributor-covenant.org/faq][FAQ]. Translations are available at [https://www.contributor-covenant.org/translations][translations].
|
||||||
|
|
||||||
|
[homepage]: https://www.contributor-covenant.org
|
||||||
|
[v2.1]: https://www.contributor-covenant.org/version/2/1/code_of_conduct.html
|
||||||
|
[Mozilla CoC]: https://github.com/mozilla/diversity
|
||||||
|
[FAQ]: https://www.contributor-covenant.org/faq
|
||||||
|
[translations]: https://www.contributor-covenant.org/translations
|
||||||
|
|||||||
@@ -13,7 +13,8 @@ RUN echo "date.timezone = \"\${PHP_TIMEZONE}\"" > /usr/local/etc/php/conf.d/time
|
|||||||
|
|
||||||
WORKDIR /app
|
WORKDIR /app
|
||||||
COPY --chown=www-data:www-data . /app
|
COPY --chown=www-data:www-data . /app
|
||||||
RUN chmod 770 /app/writable/uploads /app/writable/logs /app/writable/cache \
|
RUN chmod 750 /app/writable/logs /app/writable/uploads /app/writable/cache /app/public/uploads /app/public/uploads/item_pics \
|
||||||
|
&& chmod 640 /app/writable/uploads/importCustomers.csv \
|
||||||
&& ln -s /app/*[^public] /var/www \
|
&& ln -s /app/*[^public] /var/www \
|
||||||
&& rm -rf /var/www/html \
|
&& rm -rf /var/www/html \
|
||||||
&& ln -nsf /app/public /var/www/html
|
&& ln -nsf /app/public /var/www/html
|
||||||
|
|||||||
@@ -1,6 +1,10 @@
|
|||||||
<p align="center"><img src="https://raw.githubusercontent.com/opensourcepos/opensourcepos/master/branding/emblem.svg" alt="Open Source Point of Sale Logo" width="auto" height="200"></p>
|
<p align="center"><img src="https://raw.githubusercontent.com/opensourcepos/opensourcepos/master/branding/emblem.svg" alt="Open Source Point of Sale Logo" width="auto" height="200"></p>
|
||||||
<h3 align="center">Open Source Point of Sale</h3>
|
<h3 align="center">Open Source Point of Sale</h3>
|
||||||
|
|
||||||
|
## ☢️ Bootstrap 5 conversion WIP
|
||||||
|
|
||||||
|
This is a heavily under-construction build converting OSPOS from Bootstrap 3 to Bootstrap 5. Please do not use!
|
||||||
|
|
||||||
<p align="center">
|
<p align="center">
|
||||||
<a href="#-introduction">Introduction</a> · <a href="#-live-demo">Demo</a> · <a href="#-installation">Installation</a> ·
|
<a href="#-introduction">Introduction</a> · <a href="#-live-demo">Demo</a> · <a href="#-installation">Installation</a> ·
|
||||||
<a href="#-contributing">Contributing</a> · <a href="#-reporting-bugs">Bugs</a> · <a href="#-faq">FAQ</a> ·
|
<a href="#-contributing">Contributing</a> · <a href="#-reporting-bugs">Bugs</a> · <a href="#-faq">FAQ</a> ·
|
||||||
|
|||||||
131
SECURITY.md
131
SECURITY.md
@@ -5,8 +5,9 @@
|
|||||||
- [Supported Versions](#supported-versions)
|
- [Supported Versions](#supported-versions)
|
||||||
- [Security Advisories](#security-advisories)
|
- [Security Advisories](#security-advisories)
|
||||||
- [Reporting a Vulnerability](#reporting-a-vulnerability)
|
- [Reporting a Vulnerability](#reporting-a-vulnerability)
|
||||||
|
- [Disclosure Process](#disclosure-process)
|
||||||
|
|
||||||
<!-- END doctoc generated TOC please keep comment here to allow auto update -->
|
<!-- END doctoc generated TOC please keep comment here to allow update -->
|
||||||
|
|
||||||
# Security Policy
|
# Security Policy
|
||||||
|
|
||||||
@@ -21,26 +22,116 @@ We release patches for security vulnerabilities.
|
|||||||
|
|
||||||
## Security Advisories
|
## Security Advisories
|
||||||
|
|
||||||
The following security vulnerabilities have been published:
|
For a complete list of published and draft security advisories with CVE details, see our [GitHub Security Advisories page](https://github.com/opensourcepos/opensourcepos/security/advisories).
|
||||||
|
|
||||||
### High Severity
|
|
||||||
|
|
||||||
| CVE | Vulnerability | CVSS | Published | Fixed In | Credit |
|
|
||||||
|-----|--------------|------|-----------|----------|--------|
|
|
||||||
| [CVE-2025-68434](https://github.com/opensourcepos/opensourcepos/security/advisories/GHSA-wjm4-hfwg-5w5r) | CSRF leading to Admin Creation | 8.8 | 2025-12-17 | 3.4.2 | @Nixon-H, @jekkos |
|
|
||||||
| [CVE-2025-68147](https://github.com/opensourcepos/opensourcepos/security/advisories/GHSA-xgr7-7pvw-fpmh) | Stored XSS in Return Policy | 8.1 | 2025-12-17 | 3.4.2 | @Nixon-H, @jekkos |
|
|
||||||
| [CVE-2025-66924](https://github.com/opensourcepos/opensourcepos/security/advisories/GHSA-gv8j-f6gq-g59m) | Stored XSS in Item Kits | 7.2 | 2026-03-04 | 3.4.2 | @hungnqdz, @omkaryepre |
|
|
||||||
|
|
||||||
### Medium Severity
|
|
||||||
|
|
||||||
| CVE | Vulnerability | CVSS | Published | Fixed In | Credit |
|
|
||||||
|-----|--------------|------|-----------|----------|--------|
|
|
||||||
| [CVE-2025-68658](https://github.com/opensourcepos/opensourcepos/security/advisories/GHSA-32r8-8r9r-9chw) | Stored XSS in Company Name | 4.3 | 2026-01-13 | 3.4.2 | @hungnqdz |
|
|
||||||
|
|
||||||
For a complete list including draft advisories, see our [GitHub Security Advisories page](https://github.com/opensourcepos/opensourcepos/security/advisories).
|
|
||||||
|
|
||||||
## Reporting a Vulnerability
|
## Reporting a Vulnerability
|
||||||
|
|
||||||
Please report (suspected) security vulnerabilities to **[jeroen@steganos.dev](mailto:jeroen@steganos.dev)**.
|
**Option 1: GitHub Security Advisory (Preferred)**
|
||||||
|
|
||||||
You will receive a response from us within 48 hours. If the issue is confirmed, we will release a patch as soon as possible depending on complexity but historically within a few days.
|
1. Create a draft security advisory directly on GitHub:
|
||||||
|
- Go to https://github.com/opensourcepos/opensourcepos/security/advisories
|
||||||
|
- Click "New draft security advisory"
|
||||||
|
- Fill in the vulnerability details using our [template below](#vulnerability-template)
|
||||||
|
- Submit as **draft** (not published)
|
||||||
|
|
||||||
|
2. Notify us for triage:
|
||||||
|
- Send an email to **[jeroen@steganos.dev](mailto:jeroen@steganos.dev)** with:
|
||||||
|
- Subject: `[GHSA] Brief description of vulnerability`
|
||||||
|
- Link to the draft advisory
|
||||||
|
- Brief summary
|
||||||
|
|
||||||
|
**Option 2: Email Report**
|
||||||
|
|
||||||
|
Send vulnerability details to **[jeroen@steganos.dev](mailto:jeroen@steganos.dev)**.
|
||||||
|
|
||||||
|
You will receive a response within 48 hours. Confirmed vulnerabilities will be patched within a few days depending on complexity.
|
||||||
|
|
||||||
|
## Disclosure Process
|
||||||
|
|
||||||
|
### Timeline
|
||||||
|
|
||||||
|
| Step | Timeline | Action |
|
||||||
|
|------|----------|--------|
|
||||||
|
| 1. Report received | Day 0 | We acknowledge within 48 hours |
|
||||||
|
| 2. Triage & confirmation | Day 1-3 | We validate the vulnerability |
|
||||||
|
| 3. Fix development | Day 3-7 | We develop and test the fix |
|
||||||
|
| 4. Patch release | Day 7-10 | We release a security patch |
|
||||||
|
| 5. CVE request | Day 7-14 | We request CVE from GitHub (if applicable) |
|
||||||
|
| 6. Advisory published | Day 14 | We publish the advisory with credit |
|
||||||
|
| 7. Public disclosure | Day 14+ | Full disclosure after patch release |
|
||||||
|
|
||||||
|
### CVE Process
|
||||||
|
|
||||||
|
**We request CVE identifiers through GitHub's security advisory system.** This is the preferred and easiest method:
|
||||||
|
|
||||||
|
1. After we confirm and fix the vulnerability, we'll request a CVE through GitHub
|
||||||
|
2. GitHub coordinates with MITRE on our behalf
|
||||||
|
3. The CVE is automatically linked to the advisory
|
||||||
|
4. You'll be credited as the reporter in the published advisory
|
||||||
|
|
||||||
|
**Already have a CVE?** If you've already obtained a CVE from another source (e.g., VulDB, CVE.MITRE.ORG), please include it in your report or advisory. We'll update our advisory to reference the existing CVE.
|
||||||
|
|
||||||
|
### No Bug Bounty Program
|
||||||
|
|
||||||
|
**Important:** Open Source Point of Sale does not offer a bug bounty program.
|
||||||
|
|
||||||
|
- All security research and vulnerability triage is done on a **voluntary basis** in our free time
|
||||||
|
- We do not offer monetary rewards for vulnerability reports
|
||||||
|
- We do credit reporters in published advisories (unless anonymity is requested)
|
||||||
|
- We greatly appreciate the security research community's efforts to help improve project security
|
||||||
|
|
||||||
|
### Security Best Practices for Researchers
|
||||||
|
|
||||||
|
- **Do not** access, modify, or delete data that doesn't belong to you
|
||||||
|
- **Do not** perform denial of service attacks
|
||||||
|
- **Do not** publicly disclose vulnerabilities before we've had time to fix them
|
||||||
|
- **Do** provide sufficient information to reproduce the vulnerability
|
||||||
|
- **Do** allow us reasonable time to fix before public disclosure
|
||||||
|
- **Do** report through official channels (GitHub advisories or email)
|
||||||
|
|
||||||
|
### Vulnerability Template
|
||||||
|
|
||||||
|
When creating a draft advisory, please include:
|
||||||
|
|
||||||
|
```
|
||||||
|
## Summary
|
||||||
|
[Brief description of the vulnerability]
|
||||||
|
|
||||||
|
## Impact
|
||||||
|
- **Confidentiality:** [High/Medium/Low - what data can be exposed]
|
||||||
|
- **Integrity:** [High/Medium/Low - what can be modified]
|
||||||
|
- **Availability:** [High/Medium/Low - service disruption potential]
|
||||||
|
- **Privilege Required:** [None/Low/High - authentication level needed]
|
||||||
|
- **CVSS v3.1:** [Score] ([Vector string])
|
||||||
|
|
||||||
|
## Details
|
||||||
|
[Technical details about the vulnerability]
|
||||||
|
|
||||||
|
**Affected Code:**
|
||||||
|
```php
|
||||||
|
// Path to affected file and vulnerable code
|
||||||
|
```
|
||||||
|
|
||||||
|
**Attack Vector:**
|
||||||
|
[How an attacker can exploit this]
|
||||||
|
|
||||||
|
## Proof of Concept
|
||||||
|
```bash
|
||||||
|
# Steps to reproduce
|
||||||
|
```
|
||||||
|
|
||||||
|
## Patch
|
||||||
|
[Suggested fix or approach]
|
||||||
|
|
||||||
|
## Affected Versions
|
||||||
|
- OpenSourcePOS X.Y.Z and earlier
|
||||||
|
|
||||||
|
## Credit
|
||||||
|
[Your GitHub username or preferred name]
|
||||||
|
```
|
||||||
|
|
||||||
|
---
|
||||||
|
|
||||||
|
**Thank you to all security researchers who have contributed to making Open Source Point of Sale more secure.** Your voluntary efforts help protect thousands of users worldwide and contribute to a safer, more trustworthy free and open-source software ecosystem. We deeply appreciate your responsible disclosure and the time you invest in improving our project.
|
||||||
|
|
||||||
|
If you've reported a vulnerability and would like to discuss CVE coordination or have questions about the process, please reach out to us at [jeroen@steganos.dev](mailto:jeroen@steganos.dev).
|
||||||
@@ -58,9 +58,9 @@ class App extends BaseConfig
|
|||||||
* Allowed Hostnames in the Site URL other than the hostname in the baseURL.
|
* Allowed Hostnames in the Site URL other than the hostname in the baseURL.
|
||||||
* If you want to accept multiple Hostnames, set this.
|
* If you want to accept multiple Hostnames, set this.
|
||||||
*
|
*
|
||||||
* E.g.,
|
* Or via environment variable (useful for Docker/Compose):
|
||||||
* When your site URL ($baseURL) is 'http://example.com/', and your site
|
* ALLOWED_HOSTNAMES=example.com,www.example.com
|
||||||
* also accepts 'http://media.example.com/' and 'http://accounts.example.com/':
|
*
|
||||||
* ['media.example.com', 'accounts.example.com']
|
* ['media.example.com', 'accounts.example.com']
|
||||||
*
|
*
|
||||||
* @var list<string>
|
* @var list<string>
|
||||||
@@ -286,8 +286,10 @@ class App extends BaseConfig
|
|||||||
|
|
||||||
// Solution for CodeIgniter 4 limitation: arrays cannot be set from .env
|
// Solution for CodeIgniter 4 limitation: arrays cannot be set from .env
|
||||||
// See: https://github.com/codeigniter4/CodeIgniter4/issues/7311
|
// See: https://github.com/codeigniter4/CodeIgniter4/issues/7311
|
||||||
$envAllowedHostnames = getenv('app.allowedHostnames');
|
$envAllowedHostnames = $this->getEnvString('ALLOWED_HOSTNAMES')
|
||||||
if ($envAllowedHostnames !== false && trim($envAllowedHostnames) !== '') {
|
?? $this->getEnvString('app.allowedHostnames');
|
||||||
|
|
||||||
|
if ($envAllowedHostnames !== null) {
|
||||||
$this->allowedHostnames = array_values(array_filter(
|
$this->allowedHostnames = array_values(array_filter(
|
||||||
array_map('trim', explode(',', $envAllowedHostnames)),
|
array_map('trim', explode(',', $envAllowedHostnames)),
|
||||||
static fn (string $hostname): bool => $hostname !== ''
|
static fn (string $hostname): bool => $hostname !== ''
|
||||||
@@ -327,7 +329,7 @@ class App extends BaseConfig
|
|||||||
$errorMessage =
|
$errorMessage =
|
||||||
'Security: allowedHostnames is not configured. ' .
|
'Security: allowedHostnames is not configured. ' .
|
||||||
'Host header injection protection is disabled. ' .
|
'Host header injection protection is disabled. ' .
|
||||||
'Set app.allowedHostnames in your .env file. ' .
|
'Set app.allowedHostnames in your .env file or ALLOWED_HOSTNAMES environment variable. ' .
|
||||||
'Example: app.allowedHostnames = "example.com,www.example.com" ' .
|
'Example: app.allowedHostnames = "example.com,www.example.com" ' .
|
||||||
'Received Host: ' . $httpHost;
|
'Received Host: ' . $httpHost;
|
||||||
|
|
||||||
@@ -353,4 +355,20 @@ class App extends BaseConfig
|
|||||||
|
|
||||||
return $this->allowedHostnames[0];
|
return $this->allowedHostnames[0];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
private function getEnvString(string $key): ?string
|
||||||
|
{
|
||||||
|
$value = env($key);
|
||||||
|
|
||||||
|
if (is_string($value) && trim($value) !== '') {
|
||||||
|
return $value;
|
||||||
|
}
|
||||||
|
|
||||||
|
$raw = $_ENV[$key] ?? $_SERVER[$key] ?? getenv($key);
|
||||||
|
if (is_string($raw) && trim($raw) !== '') {
|
||||||
|
return $raw;
|
||||||
|
}
|
||||||
|
|
||||||
|
return null;
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -486,10 +486,9 @@ class Mimes
|
|||||||
/**
|
/**
|
||||||
* Attempts to determine the best mime type for the given file extension.
|
* Attempts to determine the best mime type for the given file extension.
|
||||||
*
|
*
|
||||||
* @param string $extension
|
* @return string|null The mime type found, or none if unable to determine.
|
||||||
* @return array|string|null The mime type found, or none if unable to determine.
|
|
||||||
*/
|
*/
|
||||||
public static function guessTypeFromExtension(string $extension): array|string|null
|
public static function guessTypeFromExtension(string $extension)
|
||||||
{
|
{
|
||||||
$extension = trim(strtolower($extension), '. ');
|
$extension = trim(strtolower($extension), '. ');
|
||||||
|
|
||||||
@@ -507,7 +506,7 @@ class Mimes
|
|||||||
*
|
*
|
||||||
* @return string|null The extension determined, or null if unable to match.
|
* @return string|null The extension determined, or null if unable to match.
|
||||||
*/
|
*/
|
||||||
public static function guessExtensionFromType(string $type, ?string $proposedExtension = null): ?string
|
public static function guessExtensionFromType(string $type, ?string $proposedExtension = null)
|
||||||
{
|
{
|
||||||
$type = trim(strtolower($type), '. ');
|
$type = trim(strtolower($type), '. ');
|
||||||
|
|
||||||
@@ -523,7 +522,7 @@ class Mimes
|
|||||||
}
|
}
|
||||||
|
|
||||||
// Reverse check the mime type list if no extension was proposed.
|
// Reverse check the mime type list if no extension was proposed.
|
||||||
// This search is order-sensitive!
|
// This search is order sensitive!
|
||||||
foreach (static::$mimes as $ext => $types) {
|
foreach (static::$mimes as $ext => $types) {
|
||||||
if (in_array($type, (array) $types, true)) {
|
if (in_array($type, (array) $types, true)) {
|
||||||
return $ext;
|
return $ext;
|
||||||
|
|||||||
@@ -5,7 +5,7 @@ namespace Config;
|
|||||||
use App\Models\Appconfig;
|
use App\Models\Appconfig;
|
||||||
use CodeIgniter\Cache\CacheInterface;
|
use CodeIgniter\Cache\CacheInterface;
|
||||||
use CodeIgniter\Config\BaseConfig;
|
use CodeIgniter\Config\BaseConfig;
|
||||||
use CodeIgniter\Database\Exceptions\DatabaseException;
|
use Config\Database;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class holds the configuration options stored from the database so that on launch those settings can be cached
|
* This class holds the configuration options stored from the database so that on launch those settings can be cached
|
||||||
@@ -14,7 +14,7 @@ use CodeIgniter\Database\Exceptions\DatabaseException;
|
|||||||
*/
|
*/
|
||||||
class OSPOS extends BaseConfig
|
class OSPOS extends BaseConfig
|
||||||
{
|
{
|
||||||
public array $settings;
|
public array $settings = [];
|
||||||
public string $commit_sha1 = 'dev'; // TODO: Travis scripts need to be updated to replace this with the commit hash on build
|
public string $commit_sha1 = 'dev'; // TODO: Travis scripts need to be updated to replace this with the commit hash on build
|
||||||
private CacheInterface $cache;
|
private CacheInterface $cache;
|
||||||
|
|
||||||
@@ -34,23 +34,35 @@ class OSPOS extends BaseConfig
|
|||||||
|
|
||||||
if ($cache) {
|
if ($cache) {
|
||||||
$this->settings = decode_array($cache);
|
$this->settings = decode_array($cache);
|
||||||
} else {
|
return;
|
||||||
try {
|
|
||||||
$appconfig = model(Appconfig::class);
|
|
||||||
foreach ($appconfig->get_all()->getResult() as $app_config) {
|
|
||||||
$this->settings[$app_config->key] = $app_config->value;
|
|
||||||
}
|
|
||||||
$this->cache->save('settings', encode_array($this->settings));
|
|
||||||
} catch (DatabaseException $e) {
|
|
||||||
// Database table doesn't exist yet (migrations haven't run)
|
|
||||||
// Return empty settings to allow migration page to display
|
|
||||||
$this->settings = [
|
|
||||||
'language' => 'english',
|
|
||||||
'language_code' => 'en',
|
|
||||||
'company' => 'Home'
|
|
||||||
];
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
try {
|
||||||
|
$db = Database::connect();
|
||||||
|
|
||||||
|
if (!$db->tableExists('app_config')) {
|
||||||
|
$this->settings = $this->getDefaultSettings();
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
$appconfig = model(Appconfig::class);
|
||||||
|
foreach ($appconfig->get_all()->getResult() as $app_config) {
|
||||||
|
$this->settings[$app_config->key] = $app_config->value;
|
||||||
|
}
|
||||||
|
$this->cache->save('settings', encode_array($this->settings));
|
||||||
|
} catch (\Exception $e) {
|
||||||
|
$this->settings = $this->getDefaultSettings();
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
private function getDefaultSettings(): array
|
||||||
|
{
|
||||||
|
return [
|
||||||
|
'language' => 'english',
|
||||||
|
'language_code' => 'en',
|
||||||
|
'company' => 'Home',
|
||||||
|
'barcode_type' => 'Code39'
|
||||||
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -61,4 +73,4 @@ class OSPOS extends BaseConfig
|
|||||||
$this->cache->delete('settings');
|
$this->cache->delete('settings');
|
||||||
$this->set_settings();
|
$this->set_settings();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -3,7 +3,6 @@
|
|||||||
namespace Config;
|
namespace Config;
|
||||||
|
|
||||||
use CodeIgniter\Config\BaseConfig;
|
use CodeIgniter\Config\BaseConfig;
|
||||||
use CodeIgniter\Database\Exceptions\DatabaseException;
|
|
||||||
use CodeIgniter\Session\Handlers\BaseHandler;
|
use CodeIgniter\Session\Handlers\BaseHandler;
|
||||||
use CodeIgniter\Session\Handlers\DatabaseHandler;
|
use CodeIgniter\Session\Handlers\DatabaseHandler;
|
||||||
use CodeIgniter\Session\Handlers\FileHandler;
|
use CodeIgniter\Session\Handlers\FileHandler;
|
||||||
@@ -139,7 +138,11 @@ class Session extends BaseConfig
|
|||||||
$this->driver = FileHandler::class;
|
$this->driver = FileHandler::class;
|
||||||
$this->savePath = WRITEPATH . 'session';
|
$this->savePath = WRITEPATH . 'session';
|
||||||
}
|
}
|
||||||
} catch (DatabaseException $e) {
|
} catch (\Exception $e) {
|
||||||
|
// Database not available yet (e.g. fresh install before migrations).
|
||||||
|
// Fall back to file-based sessions so the login/migration page
|
||||||
|
// can still be served. Catches mysqli_sql_exception which is
|
||||||
|
// not a subclass of DatabaseException but is a RuntimeException.
|
||||||
$this->driver = FileHandler::class;
|
$this->driver = FileHandler::class;
|
||||||
$this->savePath = WRITEPATH . 'session';
|
$this->savePath = WRITEPATH . 'session';
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -28,12 +28,9 @@ abstract class BaseController extends Controller
|
|||||||
// protected $session;
|
// protected $session;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param RequestInterface $request
|
|
||||||
* @param ResponseInterface $response
|
|
||||||
* @param LoggerInterface $logger
|
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
public function initController(RequestInterface $request, ResponseInterface $response, LoggerInterface $logger): void
|
public function initController(RequestInterface $request, ResponseInterface $response, LoggerInterface $logger)
|
||||||
{
|
{
|
||||||
// Load here all helpers you want to be available in your controllers that extend BaseController.
|
// Load here all helpers you want to be available in your controllers that extend BaseController.
|
||||||
// Caution: Do not put the this below the parent::initController() call below.
|
// Caution: Do not put the this below the parent::initController() call below.
|
||||||
|
|||||||
@@ -82,7 +82,7 @@ class Config extends Secure_Controller
|
|||||||
$npmDev = false;
|
$npmDev = false;
|
||||||
$license = [];
|
$license = [];
|
||||||
|
|
||||||
$license[$i]['title'] = 'Open Source Point Of Sale ' . config('App')->application_version;
|
$license[$i]['title'] = 'Open Source Point of Sale ' . config('App')->application_version;
|
||||||
|
|
||||||
if (file_exists('license/LICENSE')) {
|
if (file_exists('license/LICENSE')) {
|
||||||
$license[$i]['text'] = file_get_contents('license/LICENSE', false, null, 0, 3000);
|
$license[$i]['text'] = file_get_contents('license/LICENSE', false, null, 0, 3000);
|
||||||
@@ -221,6 +221,7 @@ class Config extends Secure_Controller
|
|||||||
*/
|
*/
|
||||||
public function getIndex(): string
|
public function getIndex(): string
|
||||||
{
|
{
|
||||||
|
$data['config'] = $this->config;
|
||||||
$data['stock_locations'] = $this->stock_location->get_all()->getResultArray();
|
$data['stock_locations'] = $this->stock_location->get_all()->getResultArray();
|
||||||
$data['dinner_tables'] = $this->dinner_table->get_all()->getResultArray();
|
$data['dinner_tables'] = $this->dinner_table->get_all()->getResultArray();
|
||||||
$data['customer_rewards'] = $this->customer_rewards->get_all()->getResultArray();
|
$data['customer_rewards'] = $this->customer_rewards->get_all()->getResultArray();
|
||||||
@@ -231,6 +232,8 @@ class Config extends Secure_Controller
|
|||||||
$data['line_sequence_options'] = $this->sale_lib->get_line_sequence_options();
|
$data['line_sequence_options'] = $this->sale_lib->get_line_sequence_options();
|
||||||
$data['register_mode_options'] = $this->sale_lib->get_register_mode_options();
|
$data['register_mode_options'] = $this->sale_lib->get_register_mode_options();
|
||||||
$data['invoice_type_options'] = $this->sale_lib->get_invoice_type_options();
|
$data['invoice_type_options'] = $this->sale_lib->get_invoice_type_options();
|
||||||
|
$data['keyboardShortcutOptions'] = $this->sale_lib->getKeyShortcutsOptions();
|
||||||
|
$data['keyboardShortcuts'] = $this->sale_lib->getKeyShortcuts();
|
||||||
$data['rounding_options'] = rounding_mode::get_rounding_options();
|
$data['rounding_options'] = rounding_mode::get_rounding_options();
|
||||||
$data['tax_code_options'] = $this->tax_lib->get_tax_code_options();
|
$data['tax_code_options'] = $this->tax_lib->get_tax_code_options();
|
||||||
$data['tax_category_options'] = $this->tax_lib->get_tax_category_options();
|
$data['tax_category_options'] = $this->tax_lib->get_tax_category_options();
|
||||||
@@ -368,8 +371,6 @@ class Config extends Secure_Controller
|
|||||||
public function postSaveGeneral(): ResponseInterface
|
public function postSaveGeneral(): ResponseInterface
|
||||||
{
|
{
|
||||||
$batchSaveData = [
|
$batchSaveData = [
|
||||||
'theme' => $this->request->getPost('theme'),
|
|
||||||
'login_form' => $this->request->getPost('login_form'),
|
|
||||||
'default_sales_discount_type' => $this->request->getPost('default_sales_discount_type') != null,
|
'default_sales_discount_type' => $this->request->getPost('default_sales_discount_type') != null,
|
||||||
'default_sales_discount' => parse_decimals($this->request->getPost('default_sales_discount')),
|
'default_sales_discount' => parse_decimals($this->request->getPost('default_sales_discount')),
|
||||||
'default_receivings_discount_type' => $this->request->getPost('default_receivings_discount_type') != null,
|
'default_receivings_discount_type' => $this->request->getPost('default_receivings_discount_type') != null,
|
||||||
@@ -377,8 +378,6 @@ class Config extends Secure_Controller
|
|||||||
'enforce_privacy' => $this->request->getPost('enforce_privacy') != null,
|
'enforce_privacy' => $this->request->getPost('enforce_privacy') != null,
|
||||||
'receiving_calculate_average_price' => $this->request->getPost('receiving_calculate_average_price') != null,
|
'receiving_calculate_average_price' => $this->request->getPost('receiving_calculate_average_price') != null,
|
||||||
'lines_per_page' => $this->request->getPost('lines_per_page', FILTER_SANITIZE_NUMBER_INT),
|
'lines_per_page' => $this->request->getPost('lines_per_page', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'notify_horizontal_position' => $this->request->getPost('notify_horizontal_position'),
|
|
||||||
'notify_vertical_position' => $this->request->getPost('notify_vertical_position'),
|
|
||||||
'image_max_width' => $this->request->getPost('image_max_width', FILTER_SANITIZE_NUMBER_INT),
|
'image_max_width' => $this->request->getPost('image_max_width', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'image_max_height' => $this->request->getPost('image_max_height', FILTER_SANITIZE_NUMBER_INT),
|
'image_max_height' => $this->request->getPost('image_max_height', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'image_max_size' => $this->request->getPost('image_max_size', FILTER_SANITIZE_NUMBER_INT),
|
'image_max_size' => $this->request->getPost('image_max_size', FILTER_SANITIZE_NUMBER_INT),
|
||||||
@@ -398,6 +397,9 @@ class Config extends Secure_Controller
|
|||||||
|
|
||||||
$this->module->set_show_office_group($this->request->getPost('show_office_group') != null);
|
$this->module->set_show_office_group($this->request->getPost('show_office_group') != null);
|
||||||
|
|
||||||
|
$this->db->transStart();
|
||||||
|
|
||||||
|
$attributeSuccess = true;
|
||||||
if ($batchSaveData['category_dropdown']) {
|
if ($batchSaveData['category_dropdown']) {
|
||||||
$definitionData['definition_name'] = 'ospos_category';
|
$definitionData['definition_name'] = 'ospos_category';
|
||||||
$definitionData['definition_flags'] = 0;
|
$definitionData['definition_flags'] = 0;
|
||||||
@@ -405,12 +407,36 @@ class Config extends Secure_Controller
|
|||||||
$definitionData['definition_id'] = CATEGORY_DEFINITION_ID;
|
$definitionData['definition_id'] = CATEGORY_DEFINITION_ID;
|
||||||
$definitionData['deleted'] = 0;
|
$definitionData['deleted'] = 0;
|
||||||
|
|
||||||
$this->attribute->saveDefinition($definitionData, CATEGORY_DEFINITION_ID);
|
$attributeSuccess = $this->attribute->saveDefinition($definitionData, CATEGORY_DEFINITION_ID);
|
||||||
} elseif ($batchSaveData['category_dropdown'] == NO_DEFINITION_ID) {
|
} elseif ($batchSaveData['category_dropdown'] == NO_DEFINITION_ID) {
|
||||||
$this->attribute->deleteDefinition(CATEGORY_DEFINITION_ID);
|
$attributeSuccess = $this->attribute->deleteDefinition(CATEGORY_DEFINITION_ID);
|
||||||
}
|
}
|
||||||
|
|
||||||
$success = $this->appconfig->batch_save($batchSaveData);
|
$success = $attributeSuccess && $this->appconfig->batch_save($batchSaveData);
|
||||||
|
|
||||||
|
$this->db->transComplete();
|
||||||
|
|
||||||
|
$success = $success && $this->db->transStatus();
|
||||||
|
|
||||||
|
return $this->response->setJSON(['success' => $success, 'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')]);
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Saves Appearance configuration. Used in app/Views/configs/appearance_config.php
|
||||||
|
*/
|
||||||
|
public function postSaveAppearance(): ResponseInterface
|
||||||
|
{
|
||||||
|
$batch_save_data = [
|
||||||
|
'theme' => $this->request->getPost('theme'),
|
||||||
|
'login_form' => $this->request->getPost('login_form'),
|
||||||
|
'notify_horizontal_position' => $this->request->getPost('notify_horizontal_position'),
|
||||||
|
'notify_vertical_position' => $this->request->getPost('notify_vertical_position'),
|
||||||
|
'color_mode' => $this->request->getPost('color_mode'),
|
||||||
|
'config_menu_position' => $this->request->getPost('config_menu_position'),
|
||||||
|
'responsive_design' => $this->request->getPost('responsive_design') != null
|
||||||
|
];
|
||||||
|
|
||||||
|
$success = $this->appconfig->batch_save($batch_save_data);
|
||||||
|
|
||||||
return $this->response->setJSON(['success' => $success, 'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')]);
|
return $this->response->setJSON(['success' => $success, 'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')]);
|
||||||
}
|
}
|
||||||
@@ -423,32 +449,35 @@ class Config extends Secure_Controller
|
|||||||
*/
|
*/
|
||||||
public function postCheckNumberLocale(): ResponseInterface
|
public function postCheckNumberLocale(): ResponseInterface
|
||||||
{
|
{
|
||||||
$number_locale = $this->request->getPost('number_locale');
|
$numberLocale = $this->request->getPost('number_locale');
|
||||||
$save_number_locale = $this->request->getPost('save_number_locale');
|
$saveNumberLocale = $this->request->getPost('save_number_locale');
|
||||||
|
$postedCurrencySymbol = $this->request->getPost('currency_symbol');
|
||||||
|
$postedCurrencyCode = $this->request->getPost('currency_code');
|
||||||
|
|
||||||
$fmt = new NumberFormatter($number_locale, NumberFormatter::CURRENCY);
|
$fmt = new NumberFormatter($numberLocale, NumberFormatter::CURRENCY);
|
||||||
if ($number_locale != $save_number_locale) {
|
|
||||||
$currency_symbol = $fmt->getSymbol(NumberFormatter::CURRENCY_SYMBOL);
|
// Use posted values if provided, otherwise fall back to locale defaults
|
||||||
$currency_code = $fmt->getTextAttribute(NumberFormatter::CURRENCY_CODE);
|
$currencySymbol = $postedCurrencySymbol !== '' ? $postedCurrencySymbol : $fmt->getSymbol(NumberFormatter::CURRENCY_SYMBOL);
|
||||||
$save_number_locale = $number_locale;
|
$currencyCode = $postedCurrencyCode !== '' ? $postedCurrencyCode : $fmt->getTextAttribute(NumberFormatter::CURRENCY_CODE);
|
||||||
} else {
|
|
||||||
$currency_symbol = empty($this->request->getPost('currency_symbol')) ? $fmt->getSymbol(NumberFormatter::CURRENCY_SYMBOL) : $this->request->getPost('currency_symbol');
|
// Update saved locale if it changed
|
||||||
$currency_code = empty($this->request->getPost('currency_code')) ? $fmt->getTextAttribute(NumberFormatter::CURRENCY_CODE) : $this->request->getPost('currency_code');
|
if ($numberLocale !== $saveNumberLocale) {
|
||||||
|
$saveNumberLocale = $numberLocale;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($this->request->getPost('thousands_separator') == 'false') {
|
if ($this->request->getPost('thousands_separator') == 'false') {
|
||||||
$fmt->setTextAttribute(NumberFormatter::GROUPING_SEPARATOR_SYMBOL, '');
|
$fmt->setTextAttribute(NumberFormatter::GROUPING_SEPARATOR_SYMBOL, '');
|
||||||
}
|
}
|
||||||
|
|
||||||
$fmt->setSymbol(NumberFormatter::CURRENCY_SYMBOL, $currency_symbol);
|
$fmt->setSymbol(NumberFormatter::CURRENCY_SYMBOL, $currencySymbol);
|
||||||
$number_local_example = $fmt->format(1234567890.12300);
|
$numberLocaleExample = $fmt->format(1234567890.12300);
|
||||||
|
|
||||||
return $this->response->setJSON([
|
return $this->response->setJSON([
|
||||||
'success' => $number_local_example != false,
|
'success' => $numberLocaleExample != false,
|
||||||
'save_number_locale' => $save_number_locale,
|
'save_number_locale' => $saveNumberLocale,
|
||||||
'number_locale_example' => $number_local_example,
|
'number_locale_example' => $numberLocaleExample,
|
||||||
'currency_symbol' => $currency_symbol,
|
'currency_symbol' => $currencySymbol,
|
||||||
'currency_code' => $currency_code,
|
'currency_code' => $currencyCode,
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -468,6 +497,7 @@ class Config extends Secure_Controller
|
|||||||
'currency_code' => $this->request->getPost('currency_code'),
|
'currency_code' => $this->request->getPost('currency_code'),
|
||||||
'language_code' => $exploded[0],
|
'language_code' => $exploded[0],
|
||||||
'language' => $exploded[1],
|
'language' => $exploded[1],
|
||||||
|
'rtl_language' => $this->request->getPost('rtl_language') != null,
|
||||||
'timezone' => $this->request->getPost('timezone'),
|
'timezone' => $this->request->getPost('timezone'),
|
||||||
'dateformat' => $this->request->getPost('dateformat'),
|
'dateformat' => $this->request->getPost('dateformat'),
|
||||||
'timeformat' => $this->request->getPost('timeformat'),
|
'timeformat' => $this->request->getPost('timeformat'),
|
||||||
@@ -911,7 +941,9 @@ class Config extends Secure_Controller
|
|||||||
public function postSaveReceipt(): ResponseInterface
|
public function postSaveReceipt(): ResponseInterface
|
||||||
{
|
{
|
||||||
$batch_save_data = [
|
$batch_save_data = [
|
||||||
'receipt_template' => $this->request->getPost('receipt_template'),
|
'receipt_template' => Sale_lib::isValidReceiptTemplate($this->request->getPost('receipt_template'))
|
||||||
|
? $this->request->getPost('receipt_template')
|
||||||
|
: 'receipt_default',
|
||||||
'receipt_font_size' => $this->request->getPost('receipt_font_size', FILTER_SANITIZE_NUMBER_INT),
|
'receipt_font_size' => $this->request->getPost('receipt_font_size', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'print_delay_autoreturn' => $this->request->getPost('print_delay_autoreturn', FILTER_SANITIZE_NUMBER_INT),
|
'print_delay_autoreturn' => $this->request->getPost('print_delay_autoreturn', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'email_receipt_check_behaviour' => $this->request->getPost('email_receipt_check_behaviour'),
|
'email_receipt_check_behaviour' => $this->request->getPost('email_receipt_check_behaviour'),
|
||||||
@@ -936,6 +968,44 @@ class Config extends Secure_Controller
|
|||||||
return $this->response->setJSON(['success' => $success, 'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')]);
|
return $this->response->setJSON(['success' => $success, 'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')]);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Saves keyboard shortcut bindings.
|
||||||
|
*
|
||||||
|
* @return ResponseInterface
|
||||||
|
* @noinspection PhpUnused
|
||||||
|
*/
|
||||||
|
public function postSaveShortcuts(): ResponseInterface
|
||||||
|
{
|
||||||
|
$allowedShortcuts = array_keys($this->sale_lib->getKeyShortcutsOptions());
|
||||||
|
$currentShortcuts = $this->sale_lib->getKeyShortcuts();
|
||||||
|
$batchSaveData = [];
|
||||||
|
|
||||||
|
foreach ($currentShortcuts as $name => $shortcut) {
|
||||||
|
$postedValue = trim((string)$this->request->getPost('key_' . $name));
|
||||||
|
|
||||||
|
if (!in_array($postedValue, $allowedShortcuts, true)) {
|
||||||
|
$postedValue = $shortcut['value'];
|
||||||
|
}
|
||||||
|
|
||||||
|
$batchSaveData['key_' . $name] = $postedValue;
|
||||||
|
}
|
||||||
|
|
||||||
|
$duplicateValues = array_filter(array_count_values($batchSaveData), static fn(int $count): bool => $count > 1);
|
||||||
|
if (!empty($duplicateValues)) {
|
||||||
|
return $this->response->setJSON([
|
||||||
|
'success' => false,
|
||||||
|
'message' => lang('Config.shortcuts_duplicate_bindings')
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
|
||||||
|
$success = $this->appconfig->batch_save($batchSaveData);
|
||||||
|
|
||||||
|
return $this->response->setJSON([
|
||||||
|
'success' => $success,
|
||||||
|
'message' => lang('Config.saved_' . ($success ? '' : 'un') . 'successfully')
|
||||||
|
]);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Saves invoice configuration. Used in app/Views/configs/invoice_config.php.
|
* Saves invoice configuration. Used in app/Views/configs/invoice_config.php.
|
||||||
*
|
*
|
||||||
|
|||||||
@@ -43,7 +43,7 @@ class Home extends Secure_Controller
|
|||||||
public function getChangePassword(int $employeeId = NEW_ENTRY): ResponseInterface|string
|
public function getChangePassword(int $employeeId = NEW_ENTRY): ResponseInterface|string
|
||||||
{
|
{
|
||||||
$loggedInEmployee = $this->employee->get_logged_in_employee_info();
|
$loggedInEmployee = $this->employee->get_logged_in_employee_info();
|
||||||
$currentPersonId = $loggedInEmployee->person_id;
|
$currentPersonId = (int) $loggedInEmployee->person_id;
|
||||||
|
|
||||||
$employeeId = $employeeId === NEW_ENTRY ? $currentPersonId : $employeeId;
|
$employeeId = $employeeId === NEW_ENTRY ? $currentPersonId : $employeeId;
|
||||||
|
|
||||||
@@ -68,10 +68,11 @@ class Home extends Secure_Controller
|
|||||||
public function postSave(int $employeeId = NEW_ENTRY): ResponseInterface
|
public function postSave(int $employeeId = NEW_ENTRY): ResponseInterface
|
||||||
{
|
{
|
||||||
$currentUser = $this->employee->get_logged_in_employee_info();
|
$currentUser = $this->employee->get_logged_in_employee_info();
|
||||||
|
$currentPersonId = (int) $currentUser->person_id;
|
||||||
|
|
||||||
$employeeId = $employeeId === NEW_ENTRY ? $currentUser->person_id : $employeeId;
|
$employeeId = $employeeId === NEW_ENTRY ? $currentPersonId : $employeeId;
|
||||||
|
|
||||||
if (!$this->employee->isAdmin($currentUser->person_id) && $employeeId !== $currentUser->person_id) {
|
if (!$this->employee->isAdmin($currentPersonId) && $employeeId !== $currentPersonId) {
|
||||||
return $this->response->setStatusCode(403)->setJSON([
|
return $this->response->setStatusCode(403)->setJSON([
|
||||||
'success' => false,
|
'success' => false,
|
||||||
'message' => lang('Employees.unauthorized_modify')
|
'message' => lang('Employees.unauthorized_modify')
|
||||||
|
|||||||
@@ -154,8 +154,23 @@ class Items extends Secure_Controller
|
|||||||
{
|
{
|
||||||
helper('file');
|
helper('file');
|
||||||
|
|
||||||
$pic_filename = rawurldecode($pic_filename);
|
// Security: Sanitize filename to prevent path traversal
|
||||||
$file_extension = pathinfo($pic_filename, PATHINFO_EXTENSION);
|
// Use basename() to strip directory components and prevent '../' attacks
|
||||||
|
$pic_filename = basename(rawurldecode($pic_filename));
|
||||||
|
$file_extension = strtolower(pathinfo($pic_filename, PATHINFO_EXTENSION));
|
||||||
|
|
||||||
|
// Validate file extension against system-configured allowed image types
|
||||||
|
// Handle both legacy pipe-separated and current comma-separated formats
|
||||||
|
// Fallback to types that GD library can process for thumbnail generation
|
||||||
|
$allowed_types = $this->config['image_allowed_types'] ?? 'jpg,jpeg,gif,png,webp,bmp,tif,tiff';
|
||||||
|
$allowed_extensions = strpos($allowed_types, '|') !== false
|
||||||
|
? explode('|', $allowed_types)
|
||||||
|
: explode(',', $allowed_types);
|
||||||
|
|
||||||
|
if (!in_array($file_extension, $allowed_extensions, true)) {
|
||||||
|
return $this->response->setStatusCode(400)->setBody('Invalid file type');
|
||||||
|
}
|
||||||
|
|
||||||
$images = glob("./uploads/item_pics/$pic_filename");
|
$images = glob("./uploads/item_pics/$pic_filename");
|
||||||
$base_path = './uploads/item_pics/' . pathinfo($pic_filename, PATHINFO_FILENAME);
|
$base_path = './uploads/item_pics/' . pathinfo($pic_filename, PATHINFO_FILENAME);
|
||||||
|
|
||||||
@@ -1040,14 +1055,20 @@ class Items extends Secure_Controller
|
|||||||
});
|
});
|
||||||
|
|
||||||
if (!$isFailedRow && $this->item->save_value($itemData, $itemId)) {
|
if (!$isFailedRow && $this->item->save_value($itemData, $itemId)) {
|
||||||
$this->save_tax_data($row, $itemData);
|
if (!$this->save_tax_data($row, $itemData)) {
|
||||||
$this->save_inventory_quantities($row, $itemData, $allowedStockLocations, $employeeId);
|
$isFailedRow = true;
|
||||||
|
}
|
||||||
|
if (!$this->save_inventory_quantities($row, $itemData, $allowedStockLocations, $employeeId)) {
|
||||||
|
$isFailedRow = true;
|
||||||
|
}
|
||||||
$csvAttributeValues = $this->extractAttributeData($row);
|
$csvAttributeValues = $this->extractAttributeData($row);
|
||||||
$isFailedRow = !$this->attribute->saveCSVRowAttributeData($csvAttributeValues, $itemData, $attributeData);
|
if (!$this->attribute->saveCSVRowAttributeData($csvAttributeValues, $itemData, $attributeData)) {
|
||||||
|
$isFailedRow = true;
|
||||||
|
}
|
||||||
if ($isFailedRow) {
|
if ($isFailedRow) {
|
||||||
$failedRow = $key + 2;
|
$failedRow = $key + 2;
|
||||||
$failCodes[] = $failedRow;
|
$failCodes[] = $failedRow;
|
||||||
log_message('error', "CSV Item import failed on line $failedRow while saving attributes.");
|
log_message('error', "CSV Item import failed on line $failedRow while saving item.");
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1237,13 +1258,15 @@ class Items extends Secure_Controller
|
|||||||
* @param array $item_data
|
* @param array $item_data
|
||||||
* @param array $allowed_locations
|
* @param array $allowed_locations
|
||||||
* @param int $employee_id
|
* @param int $employee_id
|
||||||
|
* @return bool Returns true on success, false on failure
|
||||||
* @throws ReflectionException
|
* @throws ReflectionException
|
||||||
*/
|
*/
|
||||||
private function save_inventory_quantities(array $row, array $item_data, array $allowed_locations, int $employee_id): void
|
private function save_inventory_quantities(array $row, array $item_data, array $allowed_locations, int $employee_id): bool
|
||||||
{
|
{
|
||||||
// Quantities & Inventory Section
|
// Quantities & Inventory Section
|
||||||
$comment = lang('Items.inventory_CSV_import_quantity');
|
$comment = lang('Items.inventory_CSV_import_quantity');
|
||||||
$is_update = (bool)$row['Id'];
|
$is_update = (bool)$row['Id'];
|
||||||
|
$success = true;
|
||||||
|
|
||||||
foreach ($allowed_locations as $location_id => $location_name) {
|
foreach ($allowed_locations as $location_id => $location_name) {
|
||||||
$item_quantity_data = ['item_id' => $item_data['item_id'], 'location_id' => $location_id];
|
$item_quantity_data = ['item_id' => $item_data['item_id'], 'location_id' => $location_id];
|
||||||
@@ -1257,20 +1280,22 @@ class Items extends Secure_Controller
|
|||||||
|
|
||||||
if (!empty($row["location_$location_name"]) || $row["location_$location_name"] === '0') {
|
if (!empty($row["location_$location_name"]) || $row["location_$location_name"] === '0') {
|
||||||
$item_quantity_data['quantity'] = $row["location_$location_name"];
|
$item_quantity_data['quantity'] = $row["location_$location_name"];
|
||||||
$this->item_quantity->save_value($item_quantity_data, $item_data['item_id'], $location_id);
|
$success &= $this->item_quantity->save_value($item_quantity_data, $item_data['item_id'], $location_id);
|
||||||
|
|
||||||
$csv_data['trans_inventory'] = $row["location_$location_name"];
|
$csv_data['trans_inventory'] = $row["location_$location_name"];
|
||||||
$this->inventory->insert($csv_data, false);
|
$success &= (bool)$this->inventory->insert($csv_data, false);
|
||||||
} elseif ($is_update) {
|
} elseif ($is_update) {
|
||||||
return;
|
continue;
|
||||||
} else {
|
} else {
|
||||||
$item_quantity_data['quantity'] = 0;
|
$item_quantity_data['quantity'] = 0;
|
||||||
$this->item_quantity->save_value($item_quantity_data, $item_data['item_id'], $location_id);
|
$success &= $this->item_quantity->save_value($item_quantity_data, $item_data['item_id'], $location_id);
|
||||||
|
|
||||||
$csv_data['trans_inventory'] = 0;
|
$csv_data['trans_inventory'] = 0;
|
||||||
$this->inventory->insert($csv_data, false);
|
$success &= (bool)$this->inventory->insert($csv_data, false);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return (bool)$success;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -1278,8 +1303,9 @@ class Items extends Secure_Controller
|
|||||||
*
|
*
|
||||||
* @param array $row
|
* @param array $row
|
||||||
* @param array $item_data
|
* @param array $item_data
|
||||||
|
* @return bool Returns true on success, false on failure
|
||||||
*/
|
*/
|
||||||
private function save_tax_data(array $row, array $item_data): void
|
private function save_tax_data(array $row, array $item_data): bool
|
||||||
{
|
{
|
||||||
$items_taxes_data = [];
|
$items_taxes_data = [];
|
||||||
|
|
||||||
@@ -1291,9 +1317,11 @@ class Items extends Secure_Controller
|
|||||||
$items_taxes_data[] = ['name' => $row['Tax 2 Name'], 'percent' => $row['Tax 2 Percent']];
|
$items_taxes_data[] = ['name' => $row['Tax 2 Name'], 'percent' => $row['Tax 2 Percent']];
|
||||||
}
|
}
|
||||||
|
|
||||||
if (isset($items_taxes_data)) {
|
if (!empty($items_taxes_data)) {
|
||||||
$this->item_taxes->save_value($items_taxes_data, $item_data['item_id']);
|
return $this->item_taxes->save_value($items_taxes_data, $item_data['item_id']);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -49,6 +49,13 @@ class Login extends BaseController
|
|||||||
return view('login', $data);
|
return view('login', $data);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if (!$data['is_latest'] || $data['is_new_install']) {
|
||||||
|
set_time_limit(3600);
|
||||||
|
|
||||||
|
$migration->setNamespace('App')->latest();
|
||||||
|
return redirect()->to('login');
|
||||||
|
}
|
||||||
|
|
||||||
$rules = ['username' => 'required|login_check[data]'];
|
$rules = ['username' => 'required|login_check[data]'];
|
||||||
$messages = [
|
$messages = [
|
||||||
'username' => [
|
'username' => [
|
||||||
@@ -62,13 +69,6 @@ class Login extends BaseController
|
|||||||
|
|
||||||
return view('login', $data);
|
return view('login', $data);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (!$data['is_latest']) {
|
|
||||||
set_time_limit(3600);
|
|
||||||
|
|
||||||
$migration->setNamespace('App')->latest();
|
|
||||||
return redirect()->to('login');
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return redirect()->to('home');
|
return redirect()->to('home');
|
||||||
@@ -79,18 +79,18 @@ class Login extends BaseController
|
|||||||
try {
|
try {
|
||||||
$migration = new MY_Migration(config('Migrations'));
|
$migration = new MY_Migration(config('Migrations'));
|
||||||
$migration->migrate_to_ci4();
|
$migration->migrate_to_ci4();
|
||||||
|
|
||||||
set_time_limit(3600);
|
set_time_limit(3600);
|
||||||
$migration->setNamespace('App')->latest();
|
$migration->setNamespace('App')->latest();
|
||||||
|
|
||||||
return $this->response->setJSON([
|
return $this->response->setJSON([
|
||||||
'success' => true,
|
'success' => true,
|
||||||
'message' => 'Migration completed successfully'
|
'message' => 'Migration completed successfully'
|
||||||
]);
|
]);
|
||||||
|
|
||||||
} catch (\Exception $e) {
|
} catch (\Exception $e) {
|
||||||
log_message('error', 'Migration failed: ' . $e->getMessage());
|
log_message('error', 'Migration failed: ' . $e->getMessage());
|
||||||
|
|
||||||
return $this->response->setJSON([
|
return $this->response->setJSON([
|
||||||
'success' => false,
|
'success' => false,
|
||||||
'message' => 'Migration failed: ' . $e->getMessage()
|
'message' => 'Migration failed: ' . $e->getMessage()
|
||||||
|
|||||||
@@ -1246,13 +1246,15 @@ class Reports extends Secure_Controller
|
|||||||
public function get_payment_type(): array
|
public function get_payment_type(): array
|
||||||
{
|
{
|
||||||
return [
|
return [
|
||||||
'all' => lang('Common.none_selected_text'),
|
'all' => lang('Common.none_selected_text'),
|
||||||
'cash' => lang('Sales.cash'),
|
'cash' => lang('Sales.cash'),
|
||||||
'due' => lang('Sales.due'),
|
'due' => lang('Sales.due'),
|
||||||
'check' => lang('Sales.check'),
|
'check' => lang('Sales.check'),
|
||||||
'credit' => lang('Sales.credit'),
|
'credit' => lang('Sales.credit'),
|
||||||
'debit' => lang('Sales.debit'),
|
'debit' => lang('Sales.debit'),
|
||||||
'invoices' => lang('Sales.invoice')
|
'bank_transfer' => lang('Sales.bank_transfer'),
|
||||||
|
'wallet' => lang('Sales.wallet'),
|
||||||
|
'invoices' => lang('Sales.invoice')
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1308,9 +1310,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $row['comment'],
|
'comment' => $row['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'sales/edit/' . $row['sale_id'],
|
'sales/edit/' . $row['sale_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
$button_key => $button_label,
|
$button_key => $button_label,
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Sales.update')
|
'title' => lang('Sales.update')
|
||||||
@@ -1435,9 +1437,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $row['comment'],
|
'comment' => $row['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'sales/edit/' . $row['sale_id'],
|
'sales/edit/' . $row['sale_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
$button_key => $button_label,
|
$button_key => $button_label,
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Sales.update')
|
'title' => lang('Sales.update')
|
||||||
@@ -1567,9 +1569,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $row['comment'],
|
'comment' => $row['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'sales/edit/' . $row['sale_id'],
|
'sales/edit/' . $row['sale_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
$button_key => $button_label,
|
$button_key => $button_label,
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Sales.update')
|
'title' => lang('Sales.update')
|
||||||
@@ -1655,9 +1657,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $report_data['comment'],
|
'comment' => $report_data['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'sales/edit/' . $report_data['sale_id'],
|
'sales/edit/' . $report_data['sale_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
$button_key => $button_label,
|
$button_key => $button_label,
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Sales.update')
|
'title' => lang('Sales.update')
|
||||||
@@ -1831,9 +1833,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $row['comment'],
|
'comment' => $row['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'sales/edit/' . $row['sale_id'],
|
'sales/edit/' . $row['sale_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
$button_key => $button_label,
|
$button_key => $button_label,
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Sales.update')
|
'title' => lang('Sales.update')
|
||||||
@@ -1911,9 +1913,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $report_data['comment'],
|
'comment' => $report_data['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'receivings/edit/' . $report_data['receiving_id'],
|
'receivings/edit/' . $report_data['receiving_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'data-btn-delete' => lang('Common.delete'),
|
'data-btn-delete' => lang('Common.delete'),
|
||||||
'title' => lang('Receivings.update')
|
'title' => lang('Receivings.update')
|
||||||
@@ -1971,9 +1973,9 @@ class Reports extends Secure_Controller
|
|||||||
'comment' => $row['comment'],
|
'comment' => $row['comment'],
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
'receivings/edit/' . $row['receiving_id'],
|
'receivings/edit/' . $row['receiving_id'],
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
'data-btn-delete' => lang('Common.delete'),
|
'data-btn-delete' => lang('Common.delete'),
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Receivings.update')
|
'title' => lang('Receivings.update')
|
||||||
|
|||||||
@@ -93,6 +93,8 @@ class Sales extends Secure_Controller
|
|||||||
'only_check' => lang('Sales.check_filter'),
|
'only_check' => lang('Sales.check_filter'),
|
||||||
'only_creditcard' => lang('Sales.credit_filter'),
|
'only_creditcard' => lang('Sales.credit_filter'),
|
||||||
'only_debit' => lang('Sales.debit'),
|
'only_debit' => lang('Sales.debit'),
|
||||||
|
'only_bank_transfer'=> lang('Sales.bank_transfer'),
|
||||||
|
'only_wallet' => lang('Sales.wallet'),
|
||||||
'only_invoices' => lang('Sales.invoice_filter'),
|
'only_invoices' => lang('Sales.invoice_filter'),
|
||||||
'selected_customer' => lang('Sales.selected_customer')
|
'selected_customer' => lang('Sales.selected_customer')
|
||||||
];
|
];
|
||||||
@@ -156,8 +158,10 @@ class Sales extends Secure_Controller
|
|||||||
'selected_customer' => false,
|
'selected_customer' => false,
|
||||||
'only_creditcard' => false,
|
'only_creditcard' => false,
|
||||||
'only_debit' => false,
|
'only_debit' => false,
|
||||||
|
'only_bank_transfer'=> false,
|
||||||
|
'only_wallet' => false,
|
||||||
'only_invoices' => $this->config['invoice_enable'] && $this->request->getGet('only_invoices', FILTER_SANITIZE_NUMBER_INT),
|
'only_invoices' => $this->config['invoice_enable'] && $this->request->getGet('only_invoices', FILTER_SANITIZE_NUMBER_INT),
|
||||||
'is_valid_receipt' => $this->sale->is_valid_receipt($search)
|
'is_valid_receipt' => $this->sale->isValidReceipt($search)
|
||||||
];
|
];
|
||||||
|
|
||||||
// Check if any filter is set in the multiselect dropdown
|
// Check if any filter is set in the multiselect dropdown
|
||||||
@@ -194,7 +198,7 @@ class Sales extends Secure_Controller
|
|||||||
? $this->request->getGet('term')
|
? $this->request->getGet('term')
|
||||||
: null;
|
: null;
|
||||||
|
|
||||||
if ($this->sale_lib->get_mode() == 'return' && $this->sale->is_valid_receipt($receipt)) {
|
if ($this->sale_lib->get_mode() == 'return' && $this->sale->isValidReceipt($receipt)) {
|
||||||
// If a valid receipt or invoice was found the search term will be replaced with a receipt number (POS #)
|
// If a valid receipt or invoice was found the search term will be replaced with a receipt number (POS #)
|
||||||
$suggestions[] = $receipt;
|
$suggestions[] = $receipt;
|
||||||
}
|
}
|
||||||
@@ -521,7 +525,7 @@ class Sales extends Secure_Controller
|
|||||||
$quantity = ($mode == 'return') ? -$quantity : $quantity;
|
$quantity = ($mode == 'return') ? -$quantity : $quantity;
|
||||||
$item_location = $this->sale_lib->get_sale_location();
|
$item_location = $this->sale_lib->get_sale_location();
|
||||||
|
|
||||||
if ($mode == 'return' && $this->sale->is_valid_receipt($item_id_or_number_or_item_kit_or_receipt)) {
|
if ($mode == 'return' && $this->sale->isValidReceipt($item_id_or_number_or_item_kit_or_receipt)) {
|
||||||
$this->sale_lib->return_entire_sale($item_id_or_number_or_item_kit_or_receipt);
|
$this->sale_lib->return_entire_sale($item_id_or_number_or_item_kit_or_receipt);
|
||||||
} elseif ($this->item_kit->is_valid_item_kit($item_id_or_number_or_item_kit_or_receipt)) {
|
} elseif ($this->item_kit->is_valid_item_kit($item_id_or_number_or_item_kit_or_receipt)) {
|
||||||
// Add kit item to order if one is assigned
|
// Add kit item to order if one is assigned
|
||||||
@@ -904,6 +908,14 @@ class Sales extends Secure_Controller
|
|||||||
return $this->_reload($data);
|
return $this->_reload($data);
|
||||||
} else {
|
} else {
|
||||||
$data['barcode'] = $this->barcode_lib->generate_receipt_barcode($data['sale_id']);
|
$data['barcode'] = $this->barcode_lib->generate_receipt_barcode($data['sale_id']);
|
||||||
|
|
||||||
|
// Validate receipt template to prevent path traversal
|
||||||
|
$receipt_template = $this->config['receipt_template'] ?? '';
|
||||||
|
if (!Sale_lib::isValidReceiptTemplate($receipt_template)) {
|
||||||
|
$receipt_template = 'receipt_default';
|
||||||
|
}
|
||||||
|
$data['receipt_template_view'] = $receipt_template;
|
||||||
|
|
||||||
$this->sale_lib->clear_all();
|
$this->sale_lib->clear_all();
|
||||||
return view('sales/receipt', $data);
|
return view('sales/receipt', $data);
|
||||||
}
|
}
|
||||||
@@ -937,7 +949,10 @@ class Sales extends Secure_Controller
|
|||||||
new Token_customer((array)$sale_data)
|
new Token_customer((array)$sale_data)
|
||||||
];
|
];
|
||||||
$text = $this->token_lib->render($text, $tokens);
|
$text = $this->token_lib->render($text, $tokens);
|
||||||
$sale_data['mimetype'] = mime_content_type(FCPATH . 'uploads/' . $this->config['company_logo']);
|
$sale_data['mimetype'] = $this->email_lib->getLogoMimeType();
|
||||||
|
|
||||||
|
// Build img_tag for email views that need it (receipt_email.php)
|
||||||
|
$sale_data['img_tag'] = $this->email_lib->buildLogoImgTag();
|
||||||
|
|
||||||
// Generate email attachment: invoice in PDF format
|
// Generate email attachment: invoice in PDF format
|
||||||
$view = Services::renderer();
|
$view = Services::renderer();
|
||||||
@@ -974,13 +989,7 @@ class Sales extends Secure_Controller
|
|||||||
|
|
||||||
if (!empty($sale_data['customer_email'])) {
|
if (!empty($sale_data['customer_email'])) {
|
||||||
$sale_data['barcode'] = $this->barcode_lib->generate_receipt_barcode($sale_data['sale_id']);
|
$sale_data['barcode'] = $this->barcode_lib->generate_receipt_barcode($sale_data['sale_id']);
|
||||||
$sale_data['img_tag'] = '';
|
$sale_data['img_tag'] = $this->email_lib->buildLogoImgTag();
|
||||||
|
|
||||||
$logo_path = FCPATH . 'uploads/' . $this->config['company_logo'];
|
|
||||||
if (!empty($this->config['company_logo']) && file_exists($logo_path)) {
|
|
||||||
$logo_data = base64_encode(file_get_contents($logo_path));
|
|
||||||
$sale_data['img_tag'] = '<img id="image" src="data:image/png;base64,' . $logo_data . '" alt="company_logo">';
|
|
||||||
}
|
|
||||||
|
|
||||||
$to = $sale_data['customer_email'];
|
$to = $sale_data['customer_email'];
|
||||||
$subject = lang('Sales.receipt');
|
$subject = lang('Sales.receipt');
|
||||||
@@ -1162,6 +1171,13 @@ class Sales extends Secure_Controller
|
|||||||
}
|
}
|
||||||
$data['invoice_view'] = $invoice_type;
|
$data['invoice_view'] = $invoice_type;
|
||||||
|
|
||||||
|
// Validate receipt template to prevent path traversal
|
||||||
|
$receipt_template = $this->config['receipt_template'] ?? '';
|
||||||
|
if (!Sale_lib::isValidReceiptTemplate($receipt_template)) {
|
||||||
|
$receipt_template = 'receipt_default';
|
||||||
|
}
|
||||||
|
$data['receipt_template_view'] = $receipt_template;
|
||||||
|
|
||||||
return $data;
|
return $data;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1256,6 +1272,7 @@ class Sales extends Secure_Controller
|
|||||||
|
|
||||||
$data['quote_number'] = $this->sale_lib->get_quote_number();
|
$data['quote_number'] = $this->sale_lib->get_quote_number();
|
||||||
$data['work_order_number'] = $this->sale_lib->get_work_order_number();
|
$data['work_order_number'] = $this->sale_lib->get_work_order_number();
|
||||||
|
$data['keyboardShortcuts'] = $this->sale_lib->getKeyShortcuts();
|
||||||
|
|
||||||
// TODO: the if/else set below should be converted to a switch
|
// TODO: the if/else set below should be converted to a switch
|
||||||
if ($this->sale_lib->get_mode() == 'sale_invoice') { // TODO: Duplicated code.
|
if ($this->sale_lib->get_mode() == 'sale_invoice') { // TODO: Duplicated code.
|
||||||
@@ -1644,7 +1661,9 @@ class Sales extends Secure_Controller
|
|||||||
*/
|
*/
|
||||||
public function getSalesKeyboardHelp(): string
|
public function getSalesKeyboardHelp(): string
|
||||||
{
|
{
|
||||||
return view('sales/help');
|
return view('sales/help', [
|
||||||
|
'keyboardShortcuts' => $this->sale_lib->getKeyShortcuts()
|
||||||
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
@@ -1,5 +1,5 @@
|
|||||||
FROM alpine:3.14
|
FROM alpine:3.14
|
||||||
MAINTAINER jekkos
|
LABEL maintainer="jekkos"
|
||||||
|
|
||||||
ADD database.sql /docker-entrypoint-initdb.d/database.sql
|
ADD database.sql /docker-entrypoint-initdb.d/database.sql
|
||||||
VOLUME /docker-entrypoint-initdb.d
|
VOLUME /docker-entrypoint-initdb.d
|
||||||
|
|||||||
@@ -2,6 +2,7 @@
|
|||||||
|
|
||||||
namespace App\Database\Migrations;
|
namespace App\Database\Migrations;
|
||||||
|
|
||||||
|
use CodeIgniter\Database\Exceptions\DatabaseException;
|
||||||
use CodeIgniter\Database\Migration;
|
use CodeIgniter\Database\Migration;
|
||||||
|
|
||||||
class Migration_Upgrade_To_3_1_1 extends Migration
|
class Migration_Upgrade_To_3_1_1 extends Migration
|
||||||
@@ -17,7 +18,37 @@ class Migration_Upgrade_To_3_1_1 extends Migration
|
|||||||
public function up(): void
|
public function up(): void
|
||||||
{
|
{
|
||||||
helper('migration');
|
helper('migration');
|
||||||
execute_script(APPPATH . 'Database/Migrations/sqlscripts/3.0.2_to_3.1.1.sql');
|
|
||||||
|
// MariaDB blocks CONVERT TO CHARACTER SET on tables with FK constraints.
|
||||||
|
// Drop all FKs across affected tables before running the SQL script, recreate after.
|
||||||
|
$fkColumns = [
|
||||||
|
['modules', 'module_id'],
|
||||||
|
['stock_locations', 'location_id'],
|
||||||
|
['permissions', 'permission_id'],
|
||||||
|
['people', 'person_id'],
|
||||||
|
['suppliers', 'supplier_id'],
|
||||||
|
['items', 'item_id'],
|
||||||
|
['item_kits', 'item_kit_id'],
|
||||||
|
['sales', 'sale_id'],
|
||||||
|
['receivings', 'receiving_id'],
|
||||||
|
['employees', 'employee_id'],
|
||||||
|
['customers', 'person_id'],
|
||||||
|
];
|
||||||
|
|
||||||
|
$constraints = [];
|
||||||
|
foreach ($fkColumns as [$table, $column]) {
|
||||||
|
foreach (dropAllForeignKeyConstraints($table, $column) as $c) {
|
||||||
|
$constraints[$c['constraintName']] = $c;
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!execute_script(APPPATH . 'Database/Migrations/sqlscripts/3.0.2_to_3.1.1.sql')) {
|
||||||
|
throw new DatabaseException('Migration script 3.0.2_to_3.1.1.sql failed. Check logs for details.');
|
||||||
|
}
|
||||||
|
|
||||||
|
$droppedTables = ['sales_suspended', 'sales_suspended_items', 'sales_suspended_items_taxes', 'sales_suspended_payments'];
|
||||||
|
$toRecreate = array_filter($constraints, fn($c) => !in_array($c['tableName'], $droppedTables, true));
|
||||||
|
recreateForeignKeyConstraints(array_values($toRecreate));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
|||||||
46
app/Database/Migrations/20260506000000_AddShortcutKeys.php
Normal file
46
app/Database/Migrations/20260506000000_AddShortcutKeys.php
Normal file
@@ -0,0 +1,46 @@
|
|||||||
|
<?php
|
||||||
|
|
||||||
|
namespace App\Database\Migrations;
|
||||||
|
|
||||||
|
use CodeIgniter\Database\Migration;
|
||||||
|
|
||||||
|
class AddShortcutKeys extends Migration
|
||||||
|
{
|
||||||
|
public function up(): void
|
||||||
|
{
|
||||||
|
$shortcutValues = [
|
||||||
|
['key' => 'key_cancel', 'value' => '27 | ESC'],
|
||||||
|
['key' => 'key_items', 'value' => '49 | ALT + 1'],
|
||||||
|
['key' => 'key_customers', 'value' => '50 | ALT + 2'],
|
||||||
|
['key' => 'key_suspend', 'value' => '51 | ALT + 3'],
|
||||||
|
['key' => 'key_suspended', 'value' => '52 | ALT + 4'],
|
||||||
|
['key' => 'key_amount', 'value' => '53 | ALT + 5'],
|
||||||
|
['key' => 'key_payment', 'value' => '54 | ALT + 6'],
|
||||||
|
['key' => 'key_complete', 'value' => '55 | ALT + 7'],
|
||||||
|
['key' => 'key_finish', 'value' => '56 | ALT + 8'],
|
||||||
|
['key' => 'key_help', 'value' => '57 | ALT + 9'],
|
||||||
|
];
|
||||||
|
|
||||||
|
$this->db->table('app_config')->ignore(true)->insertBatch($shortcutValues);
|
||||||
|
}
|
||||||
|
|
||||||
|
public function down(): void
|
||||||
|
{
|
||||||
|
$shortcutKeys = [
|
||||||
|
'key_cancel',
|
||||||
|
'key_items',
|
||||||
|
'key_customers',
|
||||||
|
'key_suspend',
|
||||||
|
'key_suspended',
|
||||||
|
'key_amount',
|
||||||
|
'key_payment',
|
||||||
|
'key_complete',
|
||||||
|
'key_finish',
|
||||||
|
'key_help',
|
||||||
|
];
|
||||||
|
|
||||||
|
$this->db->table('app_config')
|
||||||
|
->whereIn('key', $shortcutKeys)
|
||||||
|
->delete();
|
||||||
|
}
|
||||||
|
}
|
||||||
@@ -327,19 +327,6 @@ INSERT INTO `ospos_sales_items` (sale_id, item_id, description, serialnumber, li
|
|||||||
INSERT INTO `ospos_sales_payments` (sale_id, payment_type, payment_amount) SELECT sale_id, payment_type, payment_amount FROM `ospos_sales_suspended_payments`;
|
INSERT INTO `ospos_sales_payments` (sale_id, payment_type, payment_amount) SELECT sale_id, payment_type, payment_amount FROM `ospos_sales_suspended_payments`;
|
||||||
INSERT INTO `ospos_sales_items_taxes` (sale_id, item_id, line, name, percent) SELECT sale_id, item_id, line, name, percent FROM `ospos_sales_suspended_items_taxes`;
|
INSERT INTO `ospos_sales_items_taxes` (sale_id, item_id, line, name, percent) SELECT sale_id, item_id, line, name, percent FROM `ospos_sales_suspended_items_taxes`;
|
||||||
|
|
||||||
ALTER TABLE `ospos_sales_suspended_payments` DROP FOREIGN KEY `ospos_sales_suspended_payments_ibfk_1`;
|
|
||||||
|
|
||||||
ALTER TABLE `ospos_sales_suspended_items_taxes` DROP FOREIGN KEY `ospos_sales_suspended_items_taxes_ibfk_1`;
|
|
||||||
ALTER TABLE `ospos_sales_suspended_items_taxes` DROP FOREIGN KEY `ospos_sales_suspended_items_taxes_ibfk_2`;
|
|
||||||
|
|
||||||
ALTER TABLE `ospos_sales_suspended_items` DROP FOREIGN KEY `ospos_sales_suspended_items_ibfk_1`;
|
|
||||||
ALTER TABLE `ospos_sales_suspended_items` DROP FOREIGN KEY `ospos_sales_suspended_items_ibfk_2`;
|
|
||||||
ALTER TABLE `ospos_sales_suspended_items` DROP FOREIGN KEY `ospos_sales_suspended_items_ibfk_3`;
|
|
||||||
|
|
||||||
ALTER TABLE `ospos_sales_suspended` DROP FOREIGN KEY `ospos_sales_suspended_ibfk_1`;
|
|
||||||
ALTER TABLE `ospos_sales_suspended` DROP FOREIGN KEY `ospos_sales_suspended_ibfk_2`;
|
|
||||||
ALTER TABLE `ospos_sales_suspended` DROP FOREIGN KEY `ospos_sales_suspended_ibfk_3`;
|
|
||||||
|
|
||||||
DROP TABLE `ospos_sales_suspended_payments`, `ospos_sales_suspended_items_taxes`, `ospos_sales_suspended_items`, `ospos_sales_suspended`;
|
DROP TABLE `ospos_sales_suspended_payments`, `ospos_sales_suspended_items_taxes`, `ospos_sales_suspended_items`, `ospos_sales_suspended`;
|
||||||
|
|
||||||
--
|
--
|
||||||
|
|||||||
@@ -140,7 +140,7 @@ CREATE TABLE IF NOT EXISTS `ospos_expense_categories` (
|
|||||||
`category_name` varchar(255) DEFAULT NULL,
|
`category_name` varchar(255) DEFAULT NULL,
|
||||||
`category_description` varchar(255) NOT NULL,
|
`category_description` varchar(255) NOT NULL,
|
||||||
`deleted` int(1) NOT NULL DEFAULT '0'
|
`deleted` int(1) NOT NULL DEFAULT '0'
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
|
|
||||||
-- Table structure for table `ospos_expenses`
|
-- Table structure for table `ospos_expenses`
|
||||||
@@ -154,7 +154,7 @@ CREATE TABLE IF NOT EXISTS `ospos_expenses` (
|
|||||||
`description` varchar(255) NOT NULL,
|
`description` varchar(255) NOT NULL,
|
||||||
`employee_id` int(10) NOT NULL,
|
`employee_id` int(10) NOT NULL,
|
||||||
`deleted` int(1) NOT NULL DEFAULT '0'
|
`deleted` int(1) NOT NULL DEFAULT '0'
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
|
|
||||||
-- Indexes for table `ospos_expense_categories`
|
-- Indexes for table `ospos_expense_categories`
|
||||||
|
|||||||
@@ -75,7 +75,7 @@ CREATE TABLE `ospos_cash_up` (
|
|||||||
`open_employee_id` int(10) NOT NULL,
|
`open_employee_id` int(10) NOT NULL,
|
||||||
`close_employee_id` int(10) NOT NULL,
|
`close_employee_id` int(10) NOT NULL,
|
||||||
`deleted` int(1) NOT NULL DEFAULT '0'
|
`deleted` int(1) NOT NULL DEFAULT '0'
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
-- Indexes for table `ospos_cash_up`
|
-- Indexes for table `ospos_cash_up`
|
||||||
|
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ CREATE TABLE IF NOT EXISTS `ospos_tax_codes` (
|
|||||||
`state` varchar(255) NOT NULL DEFAULT '',
|
`state` varchar(255) NOT NULL DEFAULT '',
|
||||||
`deleted` int(1) NOT NULL DEFAULT 0,
|
`deleted` int(1) NOT NULL DEFAULT 0,
|
||||||
PRIMARY KEY (`tax_code_id`)
|
PRIMARY KEY (`tax_code_id`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
ALTER TABLE `ospos_customers`
|
ALTER TABLE `ospos_customers`
|
||||||
ADD COLUMN `tax_id` varchar(32) NOT NULL DEFAULT '' AFTER `taxable`,
|
ADD COLUMN `tax_id` varchar(32) NOT NULL DEFAULT '' AFTER `taxable`,
|
||||||
@@ -59,7 +59,7 @@ CREATE TABLE `ospos_sales_taxes` (
|
|||||||
`rounding_code` tinyint(2) NOT NULL DEFAULT 0,
|
`rounding_code` tinyint(2) NOT NULL DEFAULT 0,
|
||||||
PRIMARY KEY (`sales_taxes_id`),
|
PRIMARY KEY (`sales_taxes_id`),
|
||||||
KEY `print_sequence` (`sale_id`,`print_sequence`,`tax_group`)
|
KEY `print_sequence` (`sale_id`,`print_sequence`,`tax_group`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
CREATE TABLE IF NOT EXISTS `ospos_tax_jurisdictions` (
|
CREATE TABLE IF NOT EXISTS `ospos_tax_jurisdictions` (
|
||||||
`jurisdiction_id` int(11) NOT NULL AUTO_INCREMENT,
|
`jurisdiction_id` int(11) NOT NULL AUTO_INCREMENT,
|
||||||
@@ -71,7 +71,7 @@ CREATE TABLE IF NOT EXISTS `ospos_tax_jurisdictions` (
|
|||||||
`cascade_sequence` tinyint(2) NOT NULL DEFAULT 0,
|
`cascade_sequence` tinyint(2) NOT NULL DEFAULT 0,
|
||||||
`deleted` int(1) NOT NULL DEFAULT 0,
|
`deleted` int(1) NOT NULL DEFAULT 0,
|
||||||
PRIMARY KEY (`jurisdiction_id`)
|
PRIMARY KEY (`jurisdiction_id`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8 AUTO_INCREMENT=1;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci AUTO_INCREMENT=1;
|
||||||
|
|
||||||
ALTER TABLE `ospos_suppliers`
|
ALTER TABLE `ospos_suppliers`
|
||||||
ADD COLUMN `tax_id` varchar(32) DEFAULT NULL AFTER `account_number`;
|
ADD COLUMN `tax_id` varchar(32) DEFAULT NULL AFTER `account_number`;
|
||||||
@@ -89,7 +89,7 @@ CREATE TABLE IF NOT EXISTS `ospos_tax_rates` (
|
|||||||
`tax_rate` decimal(15,4) NOT NULL DEFAULT 0.0000,
|
`tax_rate` decimal(15,4) NOT NULL DEFAULT 0.0000,
|
||||||
`tax_rounding_code` tinyint(2) NOT NULL DEFAULT 0,
|
`tax_rounding_code` tinyint(2) NOT NULL DEFAULT 0,
|
||||||
PRIMARY KEY (`tax_rate_id`)
|
PRIMARY KEY (`tax_rate_id`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
-- Add support for sales tax report
|
-- Add support for sales tax report
|
||||||
|
|
||||||
|
|||||||
@@ -12,7 +12,7 @@ CREATE TABLE `ospos_sales_payments` (
|
|||||||
`reference_code` varchar(40) NOT NULL DEFAULT '',
|
`reference_code` varchar(40) NOT NULL DEFAULT '',
|
||||||
PRIMARY KEY (`payment_id`),
|
PRIMARY KEY (`payment_id`),
|
||||||
KEY `payment_sale` (`sale_id`, `payment_type`)
|
KEY `payment_sale` (`sale_id`, `payment_type`)
|
||||||
) ENGINE=InnoDB DEFAULT CHARSET=utf8;
|
) ENGINE=InnoDB DEFAULT CHARSET=utf8 COLLATE=utf8_general_ci;
|
||||||
|
|
||||||
INSERT INTO ospos_sales_payments (sale_id, payment_type, payment_amount, payment_user)
|
INSERT INTO ospos_sales_payments (sale_id, payment_type, payment_amount, payment_user)
|
||||||
SELECT payments.sale_id, payments.payment_type, payments.payment_amount, sales.employee_id
|
SELECT payments.sale_id, payments.payment_type, payments.payment_amount, sales.employee_id
|
||||||
|
|||||||
@@ -79,10 +79,14 @@ INSERT INTO `ospos_app_config` (`key`, `value`) VALUES
|
|||||||
('smtp_timeout', '5'),
|
('smtp_timeout', '5'),
|
||||||
('smtp_crypto', 'ssl'),
|
('smtp_crypto', 'ssl'),
|
||||||
('receipt_template', 'receipt_default'),
|
('receipt_template', 'receipt_default'),
|
||||||
('theme', 'flatly'),
|
('theme', 'bootstrap'),
|
||||||
('statistics', '1'),
|
('statistics', '1'),
|
||||||
('language', 'english'),
|
('language', 'english'),
|
||||||
('language_code', 'en');
|
('language_code', 'en'),
|
||||||
|
('rtl_language', '0'),
|
||||||
|
('color_mode', 'light'),
|
||||||
|
('config_menu_position', 'start'),
|
||||||
|
('responsive_design', '1');
|
||||||
|
|
||||||
|
|
||||||
-- --------------------------------------------------------
|
-- --------------------------------------------------------
|
||||||
|
|||||||
@@ -22,7 +22,7 @@ function current_language_code(bool $load_system_language = false): string
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $config->language_code ?? DEFAULT_LANGUAGE_CODE;
|
return $config['language_code'] ?? DEFAULT_LANGUAGE_CODE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -43,7 +43,7 @@ function current_language(bool $load_system_language = false): string
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $config->language ?? DEFAULT_LANGUAGE_CODE;
|
return $config['language'] ?? DEFAULT_LANGUAGE;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -272,6 +272,9 @@ function get_payment_options(): array
|
|||||||
$payments[lang('Sales.upi')] = lang('Sales.upi');
|
$payments[lang('Sales.upi')] = lang('Sales.upi');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$payments[lang('Sales.bank_transfer')] = lang('Sales.bank_transfer');
|
||||||
|
$payments[lang('Sales.wallet')] = lang('Sales.wallet');
|
||||||
|
|
||||||
return $payments;
|
return $payments;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -172,6 +172,7 @@ function dropAllForeignKeyConstraints(string $table, string $column): array {
|
|||||||
WHERE kcu.TABLE_SCHEMA = DATABASE()
|
WHERE kcu.TABLE_SCHEMA = DATABASE()
|
||||||
AND ((kcu.REFERENCED_TABLE_NAME = '" . $db->getPrefix() . "$table' AND kcu.REFERENCED_COLUMN_NAME = '$column')
|
AND ((kcu.REFERENCED_TABLE_NAME = '" . $db->getPrefix() . "$table' AND kcu.REFERENCED_COLUMN_NAME = '$column')
|
||||||
OR (kcu.TABLE_NAME = '" . $db->getPrefix() . "$table' AND kcu.COLUMN_NAME = '$column'))
|
OR (kcu.TABLE_NAME = '" . $db->getPrefix() . "$table' AND kcu.COLUMN_NAME = '$column'))
|
||||||
|
AND rc.CONSTRAINT_NAME IS NOT NULL
|
||||||
");
|
");
|
||||||
|
|
||||||
$deletedConstraints = [];
|
$deletedConstraints = [];
|
||||||
|
|||||||
@@ -118,21 +118,21 @@ function get_sale_data_row(object $sale): array
|
|||||||
? '-'
|
? '-'
|
||||||
: anchor(
|
: anchor(
|
||||||
"$controller/invoice/$sale->sale_id",
|
"$controller/invoice/$sale->sale_id",
|
||||||
'<span class="glyphicon glyphicon-list-alt"></span>',
|
'<i class="bi bi-file-text"></i>',
|
||||||
['title' => lang('Sales.show_invoice')]
|
['title' => lang('Sales.show_invoice')]
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
$row['receipt'] = anchor(
|
$row['receipt'] = anchor(
|
||||||
"$controller/receipt/$sale->sale_id",
|
"$controller/receipt/$sale->sale_id",
|
||||||
'<span class="glyphicon glyphicon-usd"></span>',
|
'<i class="bi bi-receipt"></i>',
|
||||||
['title' => lang('Sales.show_receipt')]
|
['title' => lang('Sales.show_receipt')]
|
||||||
);
|
);
|
||||||
$row['edit'] = anchor(
|
$row['edit'] = anchor(
|
||||||
"$controller/edit/$sale->sale_id",
|
"$controller/edit/$sale->sale_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg print_hide',
|
'class' => 'modal-launch print_hide',
|
||||||
'data-btn-delete' => lang('Common.delete'),
|
'data-btn-delete' => lang('Common.delete'),
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
@@ -232,18 +232,18 @@ function get_person_data_row(object $person): array
|
|||||||
? ''
|
? ''
|
||||||
: anchor(
|
: anchor(
|
||||||
"Messages/view/$person->person_id",
|
"Messages/view/$person->person_id",
|
||||||
'<span class="glyphicon glyphicon-phone"></span>',
|
'<i class="bi bi-telephone"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Messages.sms_send')
|
'title' => lang('Messages.sms_send')
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$person->person_id",
|
"$controller/view/$person->person_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . '.update') // TODO: String interpolation
|
'title' => lang(ucfirst($controller) . '.update') // TODO: String interpolation
|
||||||
]
|
]
|
||||||
@@ -299,18 +299,18 @@ function get_customer_data_row(object $person, object $stats): array
|
|||||||
? ''
|
? ''
|
||||||
: anchor(
|
: anchor(
|
||||||
"Messages/view/$person->person_id",
|
"Messages/view/$person->person_id",
|
||||||
'<span class="glyphicon glyphicon-phone"></span>',
|
'<i class="bi bi-telephone"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Messages.sms_send')
|
'title' => lang('Messages.sms_send')
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$person->person_id",
|
"$controller/view/$person->person_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -369,18 +369,18 @@ function get_supplier_data_row(object $supplier): array
|
|||||||
? ''
|
? ''
|
||||||
: anchor(
|
: anchor(
|
||||||
"Messages/view/$supplier->person_id",
|
"Messages/view/$supplier->person_id",
|
||||||
'<span class="glyphicon glyphicon-phone"></span>',
|
'<i class="bi bi-telephone"></i>',
|
||||||
[
|
[
|
||||||
'class' => "modal-dlg",
|
'class' => "modal-launch",
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang('Messages.sms_send')
|
'title' => lang('Messages.sms_send')
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$supplier->person_id",
|
"$controller/view/$supplier->person_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => "modal-dlg",
|
'class' => "modal-launch",
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -498,26 +498,26 @@ function get_item_data_row(object $item): array
|
|||||||
$icons = [
|
$icons = [
|
||||||
'inventory' => anchor(
|
'inventory' => anchor(
|
||||||
"$controller/inventory/$item->item_id",
|
"$controller/inventory/$item->item_id",
|
||||||
'<span class="glyphicon glyphicon-pushpin"></span>',
|
'<i class="bi bi-box"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".count")
|
'title' => lang(ucfirst($controller) . ".count")
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
'stock' => anchor(
|
'stock' => anchor(
|
||||||
"$controller/countDetails/$item->item_id",
|
"$controller/countDetails/$item->item_id",
|
||||||
'<span class="glyphicon glyphicon-list-alt"></span>',
|
'<i class="bi bi-info-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'title' => lang(ucfirst($controller) . ".details_count")
|
'title' => lang(ucfirst($controller) . ".details_count")
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$item->item_id",
|
"$controller/view/$item->item_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -561,9 +561,9 @@ function get_giftcard_data_row(object $giftcard): array
|
|||||||
'value' => to_currency($giftcard->value),
|
'value' => to_currency($giftcard->value),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$giftcard->giftcard_id",
|
"$controller/view/$giftcard->giftcard_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -607,9 +607,9 @@ function get_item_kit_data_row(object $item_kit): array
|
|||||||
'total_unit_price' => to_currency($item_kit->total_unit_price),
|
'total_unit_price' => to_currency($item_kit->total_unit_price),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$item_kit->item_kit_id",
|
"$controller/view/$item_kit->item_kit_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -715,9 +715,9 @@ function get_attribute_definition_data_row(object $attribute_row): array
|
|||||||
'definition_flags' => $definition_flags,
|
'definition_flags' => $definition_flags,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$attribute_row->definition_id",
|
"$controller/view/$attribute_row->definition_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -755,9 +755,9 @@ function get_expense_category_data_row(object $expense_category): array
|
|||||||
'category_description' => $expense_category->category_description,
|
'category_description' => $expense_category->category_description,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$expense_category->expense_category_id",
|
"$controller/view/$expense_category->expense_category_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -809,9 +809,9 @@ function get_expenses_data_row(object $expense): array
|
|||||||
'created_by' => $expense->first_name . ' ' . $expense->last_name,
|
'created_by' => $expense->first_name . ' ' . $expense->last_name,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$expense->expense_id",
|
"$controller/view/$expense->expense_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
@@ -904,16 +904,16 @@ function get_cash_up_data_row(object $cash_up): array
|
|||||||
'close_date' => to_datetime(strtotime($cash_up->close_date)),
|
'close_date' => to_datetime(strtotime($cash_up->close_date)),
|
||||||
'close_employee_id' => $cash_up->close_first_name . ' ' . $cash_up->close_last_name,
|
'close_employee_id' => $cash_up->close_first_name . ' ' . $cash_up->close_last_name,
|
||||||
'closed_amount_cash' => to_currency($cash_up->closed_amount_cash),
|
'closed_amount_cash' => to_currency($cash_up->closed_amount_cash),
|
||||||
'note' => $cash_up->note ? '<span class="glyphicon glyphicon-ok"></span>' : '<span class="glyphicon glyphicon-remove"></span>',
|
'note' => $cash_up->note ? '<i class="bi bi-check-lg"></i>' : '<i class="bi bi-x-lg"></i>',
|
||||||
'closed_amount_due' => to_currency($cash_up->closed_amount_due),
|
'closed_amount_due' => to_currency($cash_up->closed_amount_due),
|
||||||
'closed_amount_card' => to_currency($cash_up->closed_amount_card),
|
'closed_amount_card' => to_currency($cash_up->closed_amount_card),
|
||||||
'closed_amount_check' => to_currency($cash_up->closed_amount_check),
|
'closed_amount_check' => to_currency($cash_up->closed_amount_check),
|
||||||
'closed_amount_total' => to_currency($cash_up->closed_amount_total),
|
'closed_amount_total' => to_currency($cash_up->closed_amount_total),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller/view/$cash_up->cashup_id",
|
"$controller/view/$cash_up->cashup_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller) . ".update")
|
'title' => lang(ucfirst($controller) . ".update")
|
||||||
]
|
]
|
||||||
|
|||||||
@@ -36,9 +36,9 @@ function get_tax_code_data_row($tax_code_row): array
|
|||||||
'state' => $tax_code_row->state,
|
'state' => $tax_code_row->state,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller_name/view_tax_codes/$tax_code_row->tax_code",
|
"$controller_name/view_tax_codes/$tax_code_row->tax_code",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller_name) . ".update_tax_codes")
|
'title' => lang(ucfirst($controller_name) . ".update_tax_codes")
|
||||||
]
|
]
|
||||||
@@ -74,9 +74,9 @@ function get_tax_categories_data_row($tax_categories_row): array
|
|||||||
'tax_group_sequence' => $tax_categories_row->tax_group_sequence,
|
'tax_group_sequence' => $tax_categories_row->tax_group_sequence,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller_name/view/$tax_categories_row->tax_category_id",
|
"$controller_name/view/$tax_categories_row->tax_category_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller_name) . ".update")
|
'title' => lang(ucfirst($controller_name) . ".update")
|
||||||
]
|
]
|
||||||
@@ -111,9 +111,9 @@ function get_tax_jurisdictions_data_row($tax_jurisdiction_row): array
|
|||||||
'reporting_authority' => $tax_jurisdiction_row->reporting_authority,
|
'reporting_authority' => $tax_jurisdiction_row->reporting_authority,
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller_name/view/$tax_jurisdiction_row->jurisdiction_id",
|
"$controller_name/view/$tax_jurisdiction_row->jurisdiction_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller_name) . ".update")
|
'title' => lang(ucfirst($controller_name) . ".update")
|
||||||
]
|
]
|
||||||
@@ -156,9 +156,9 @@ function get_tax_rates_data_row($tax_rates_row): array
|
|||||||
'rounding_code_name' => Rounding_mode::get_rounding_code_name($tax_rates_row->tax_rounding_code),
|
'rounding_code_name' => Rounding_mode::get_rounding_code_name($tax_rates_row->tax_rounding_code),
|
||||||
'edit' => anchor(
|
'edit' => anchor(
|
||||||
"$controller_name/view/$tax_rates_row->tax_rate_id",
|
"$controller_name/view/$tax_rates_row->tax_rate_id",
|
||||||
'<span class="glyphicon glyphicon-edit"></span>',
|
'<i class="bi bi-pencil-square"></i>',
|
||||||
[
|
[
|
||||||
'class' => 'modal-dlg',
|
'class' => 'modal-launch',
|
||||||
'data-btn-submit' => lang('Common.submit'),
|
'data-btn-submit' => lang('Common.submit'),
|
||||||
'title' => lang(ucfirst($controller_name) . ".update")
|
'title' => lang(ucfirst($controller_name) . ".update")
|
||||||
]
|
]
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ return [
|
|||||||
"amount_due" => "Amount Due",
|
"amount_due" => "Amount Due",
|
||||||
"amount_tendered" => "Amount Tendered",
|
"amount_tendered" => "Amount Tendered",
|
||||||
"authorized_signature" => "Authorised Signature",
|
"authorized_signature" => "Authorised Signature",
|
||||||
|
"bank_transfer" => "Bank Transfer",
|
||||||
"cancel_sale" => "Cancel",
|
"cancel_sale" => "Cancel",
|
||||||
"cash" => "Cash",
|
"cash" => "Cash",
|
||||||
"cash_1" => "",
|
"cash_1" => "",
|
||||||
@@ -223,6 +224,7 @@ return [
|
|||||||
"update" => "Update",
|
"update" => "Update",
|
||||||
"upi" => "UPI",
|
"upi" => "UPI",
|
||||||
"visa" => "",
|
"visa" => "",
|
||||||
|
"wallet" => "Wallet",
|
||||||
"wholesale" => "",
|
"wholesale" => "",
|
||||||
"work_order" => "Work Order",
|
"work_order" => "Work Order",
|
||||||
"work_order_number" => "Work Order Number",
|
"work_order_number" => "Work Order Number",
|
||||||
|
|||||||
@@ -302,6 +302,10 @@ return [
|
|||||||
"suggestions_layout" => "Search Suggestions Layout",
|
"suggestions_layout" => "Search Suggestions Layout",
|
||||||
"suggestions_second_column" => "Column 2",
|
"suggestions_second_column" => "Column 2",
|
||||||
"suggestions_third_column" => "Column 3",
|
"suggestions_third_column" => "Column 3",
|
||||||
|
"shortcuts" => "Shortcuts",
|
||||||
|
"shortcuts_configuration" => "Sales Keyboard Shortcut Configuration",
|
||||||
|
"shortcuts_duplicate_bindings" => "Shortcut bindings must be unique.",
|
||||||
|
"shortcuts_save_error" => "Unable to save shortcut settings.",
|
||||||
"system_conf" => "Setup & Conf",
|
"system_conf" => "Setup & Conf",
|
||||||
"system_info" => "System Info",
|
"system_info" => "System Info",
|
||||||
"table" => "Table",
|
"table" => "Table",
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ return [
|
|||||||
"amount_due" => "Amount Due",
|
"amount_due" => "Amount Due",
|
||||||
"amount_tendered" => "Amount Tendered",
|
"amount_tendered" => "Amount Tendered",
|
||||||
"authorized_signature" => "Authorized Signature",
|
"authorized_signature" => "Authorized Signature",
|
||||||
|
"bank_transfer" => "Bank Transfer",
|
||||||
"cancel_sale" => "Cancel",
|
"cancel_sale" => "Cancel",
|
||||||
"cash" => "Cash",
|
"cash" => "Cash",
|
||||||
"cash_1" => "",
|
"cash_1" => "",
|
||||||
@@ -223,6 +224,7 @@ return [
|
|||||||
"update" => "Update",
|
"update" => "Update",
|
||||||
"upi" => "UPI",
|
"upi" => "UPI",
|
||||||
"visa" => "",
|
"visa" => "",
|
||||||
|
"wallet" => "Wallet",
|
||||||
"wholesale" => "",
|
"wholesale" => "",
|
||||||
"work_order" => "Work Order",
|
"work_order" => "Work Order",
|
||||||
"work_order_number" => "Work Order Number",
|
"work_order_number" => "Work Order Number",
|
||||||
|
|||||||
@@ -26,7 +26,7 @@ return [
|
|||||||
"cost_price_required" => "Precio al Por Mayor es un campo requerido.",
|
"cost_price_required" => "Precio al Por Mayor es un campo requerido.",
|
||||||
"count" => "Actualizar Inventario",
|
"count" => "Actualizar Inventario",
|
||||||
"csv_import_failed" => "Falló la importación de Hoja de Cálculo",
|
"csv_import_failed" => "Falló la importación de Hoja de Cálculo",
|
||||||
"csv_import_invalid_location" => "Ubicación(es) de stock inválida(s) encontrada(s): {0}. Solo ubicaciones de stock válidas son permitidas.",
|
"csv_import_invalid_location" => "Se encontraron ubicaciones de stock no válidas: {0}. Solo se permiten ubicaciones de stock válidas.",
|
||||||
"csv_import_nodata_wrongformat" => "El archivo subido no tiene datos o el formato es incorrecto.",
|
"csv_import_nodata_wrongformat" => "El archivo subido no tiene datos o el formato es incorrecto.",
|
||||||
"csv_import_partially_failed" => "Hubo {0} falla(s) en la importación de producto(s) en la(s) línea(s): {1}. Ninguna fila ha sido importada.",
|
"csv_import_partially_failed" => "Hubo {0} falla(s) en la importación de producto(s) en la(s) línea(s): {1}. Ninguna fila ha sido importada.",
|
||||||
"csv_import_success" => "Se importaron los articulos exitosamente.",
|
"csv_import_success" => "Se importaron los articulos exitosamente.",
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ return [
|
|||||||
"amount_due" => "Monto Adeudado",
|
"amount_due" => "Monto Adeudado",
|
||||||
"amount_tendered" => "Cantidad Recibida",
|
"amount_tendered" => "Cantidad Recibida",
|
||||||
"authorized_signature" => "Firma Autorizada",
|
"authorized_signature" => "Firma Autorizada",
|
||||||
|
"bank_transfer" => "Transferencia Bancaria",
|
||||||
"cancel_sale" => "Cancelar Venta",
|
"cancel_sale" => "Cancelar Venta",
|
||||||
"cash" => "Efectivo",
|
"cash" => "Efectivo",
|
||||||
"cash_1" => "1",
|
"cash_1" => "1",
|
||||||
@@ -222,6 +223,7 @@ return [
|
|||||||
"update" => "Editar",
|
"update" => "Editar",
|
||||||
"upi" => "PIN UPI",
|
"upi" => "PIN UPI",
|
||||||
"visa" => "Tarjeta Visa",
|
"visa" => "Tarjeta Visa",
|
||||||
|
"wallet" => "Monedero",
|
||||||
"wholesale" => "Precio al por mayor",
|
"wholesale" => "Precio al por mayor",
|
||||||
"work_order" => "Orden trabajo",
|
"work_order" => "Orden trabajo",
|
||||||
"work_order_number" => "Numero Orden Trabajo",
|
"work_order_number" => "Numero Orden Trabajo",
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ return [
|
|||||||
"amount_due" => "Monto de adeudo",
|
"amount_due" => "Monto de adeudo",
|
||||||
"amount_tendered" => "Cantidad Recibida",
|
"amount_tendered" => "Cantidad Recibida",
|
||||||
"authorized_signature" => "Firma Autorizada",
|
"authorized_signature" => "Firma Autorizada",
|
||||||
|
"bank_transfer" => "Transferencia Bancaria",
|
||||||
"cancel_sale" => "Cancelar",
|
"cancel_sale" => "Cancelar",
|
||||||
"cash" => "Efectivo",
|
"cash" => "Efectivo",
|
||||||
"cash_1" => "",
|
"cash_1" => "",
|
||||||
@@ -222,6 +223,7 @@ return [
|
|||||||
"update" => "Actualizar",
|
"update" => "Actualizar",
|
||||||
"upi" => "UPI",
|
"upi" => "UPI",
|
||||||
"visa" => "",
|
"visa" => "",
|
||||||
|
"wallet" => "Monedero",
|
||||||
"wholesale" => "",
|
"wholesale" => "",
|
||||||
"work_order" => "Orden de trabajo",
|
"work_order" => "Orden de trabajo",
|
||||||
"work_order_number" => "Número de orden de trabajo",
|
"work_order_number" => "Número de orden de trabajo",
|
||||||
|
|||||||
@@ -9,6 +9,7 @@ return [
|
|||||||
"amount_due" => "Montant à Payer",
|
"amount_due" => "Montant à Payer",
|
||||||
"amount_tendered" => "Montant Présenté",
|
"amount_tendered" => "Montant Présenté",
|
||||||
"authorized_signature" => "Signature autorisée",
|
"authorized_signature" => "Signature autorisée",
|
||||||
|
"bank_transfer" => "Virement Bancaire",
|
||||||
"cancel_sale" => "Annuler la Vente",
|
"cancel_sale" => "Annuler la Vente",
|
||||||
"cash" => "Espèce",
|
"cash" => "Espèce",
|
||||||
"cash_1" => "",
|
"cash_1" => "",
|
||||||
@@ -222,6 +223,7 @@ return [
|
|||||||
"update" => "Éditer",
|
"update" => "Éditer",
|
||||||
"upi" => "UPI",
|
"upi" => "UPI",
|
||||||
"visa" => "",
|
"visa" => "",
|
||||||
|
"wallet" => "Portefeuille",
|
||||||
"wholesale" => "",
|
"wholesale" => "",
|
||||||
"work_order" => "Commande de travail",
|
"work_order" => "Commande de travail",
|
||||||
"work_order_number" => "Numéro de commande",
|
"work_order_number" => "Numéro de commande",
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ return [
|
|||||||
"february" => "",
|
"february" => "",
|
||||||
"march" => "",
|
"march" => "",
|
||||||
"april" => "",
|
"april" => "",
|
||||||
"mayl" => "",
|
"may" => "",
|
||||||
"june" => "",
|
"june" => "",
|
||||||
"july" => "",
|
"july" => "",
|
||||||
"august" => "",
|
"august" => "",
|
||||||
@@ -46,4 +46,4 @@ return [
|
|||||||
"october" => "",
|
"october" => "",
|
||||||
"november" => "",
|
"november" => "",
|
||||||
"december" => "",
|
"december" => "",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ return [
|
|||||||
"february" => "",
|
"february" => "",
|
||||||
"march" => "",
|
"march" => "",
|
||||||
"april" => "",
|
"april" => "",
|
||||||
"mayl" => "",
|
"may" => "",
|
||||||
"june" => "",
|
"june" => "",
|
||||||
"july" => "",
|
"july" => "",
|
||||||
"august" => "",
|
"august" => "",
|
||||||
@@ -46,4 +46,4 @@ return [
|
|||||||
"october" => "",
|
"october" => "",
|
||||||
"november" => "",
|
"november" => "",
|
||||||
"december" => "",
|
"december" => "",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ return [
|
|||||||
"february" => "ഫെബ്രുവരി",
|
"february" => "ഫെബ്രുവരി",
|
||||||
"march" => "മാർച്ച്",
|
"march" => "മാർച്ച്",
|
||||||
"april" => "ഏപ്രിൽ",
|
"april" => "ഏപ്രിൽ",
|
||||||
"mayl" => "മേയ്",
|
"may" => "മേയ്",
|
||||||
"june" => "ജൂൺ",
|
"june" => "ജൂൺ",
|
||||||
"july" => "ജൂലൈ",
|
"july" => "ജൂലൈ",
|
||||||
"august" => "ആഗസ്റ്റ്",
|
"august" => "ആഗസ്റ്റ്",
|
||||||
@@ -46,4 +46,4 @@ return [
|
|||||||
"october" => "ഒക്ടോബർ",
|
"october" => "ഒക്ടോബർ",
|
||||||
"november" => "നവംബർ",
|
"november" => "നവംബർ",
|
||||||
"december" => "ഡിസംബർ",
|
"december" => "ഡിസംബർ",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -38,7 +38,7 @@ return [
|
|||||||
"february" => "Februar",
|
"february" => "Februar",
|
||||||
"march" => "Mars",
|
"march" => "Mars",
|
||||||
"april" => "April",
|
"april" => "April",
|
||||||
"mayl" => "Mai",
|
"may" => "Mai",
|
||||||
"june" => "Juni",
|
"june" => "Juni",
|
||||||
"july" => "Juli",
|
"july" => "Juli",
|
||||||
"august" => "August",
|
"august" => "August",
|
||||||
@@ -46,4 +46,4 @@ return [
|
|||||||
"october" => "Oktober",
|
"october" => "Oktober",
|
||||||
"november" => "November",
|
"november" => "November",
|
||||||
"december" => "Desember",
|
"december" => "Desember",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -1,12 +1,12 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
return [
|
return [
|
||||||
"all" => "ทั้งหมด",
|
'all' => "ทั้งหมด",
|
||||||
"columns" => "คอลัมน์",
|
'columns' => "คอลัมน์",
|
||||||
"hide_show_pagination" => "ซ่อน/แสดง รายการหน้า",
|
'hide_show_pagination' => "ซ่อน/แสดง รายการหน้า",
|
||||||
"loading" => "กำลังดำเนินการ รอสักครู่",
|
'loading' => "กำลังดำเนินการ รอสักครู่ ...",
|
||||||
"page_from_to" => "แสดง {0} ถึง {1} จาก {2} รายการ",
|
'page_from_to' => "แสดง {0} ถึง {1} จาก {2} รายการ",
|
||||||
"refresh" => "Refresh ข้อมูล",
|
'refresh' => "Refresh ข้อมูล",
|
||||||
"rows_per_page" => "{0} รายการ/หน้า",
|
'rows_per_page' => "{0} รายการ/หน้า",
|
||||||
"toggle" => "ซ่อน/แสดง",
|
'toggle' => "ซ่อน/แสดง",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -9,7 +9,9 @@ return [
|
|||||||
"login" => "ลงชื่อเข้าใช้",
|
"login" => "ลงชื่อเข้าใช้",
|
||||||
"logout" => "ออกจากระบบ",
|
"logout" => "ออกจากระบบ",
|
||||||
"migration_needed" => "การย้ายฐานข้อมูลไปยัง {0} จะเริ่มต้นหลังจากเข้าสู่ระบบ",
|
"migration_needed" => "การย้ายฐานข้อมูลไปยัง {0} จะเริ่มต้นหลังจากเข้าสู่ระบบ",
|
||||||
"migration_required" => "",
|
"migration_required" => "จําเป็นต้องมีการปรับปรุงฐานข้อมูล",
|
||||||
|
"migration_auth_message" => "ผู้ดูแลระบบจำเป็นต้องมีสิทธิ์ในการปรับปรุงฐานข้อมูลเวอร์ชั่น {0} กรุณาเข้าระบบเพื่อดำเนินการต่อ",
|
||||||
|
"migration_complete_redirect" => "ทำการปรับปรุงฐานข้อมูลเรียบร้อย กำลังดำเนินการไปหน้าเข้าสู่ระบบ ...",
|
||||||
"migration_auth_message" => "",
|
"migration_auth_message" => "",
|
||||||
"migration_initializing" => "",
|
"migration_initializing" => "",
|
||||||
"migration_running" => "",
|
"migration_running" => "",
|
||||||
@@ -17,7 +19,6 @@ return [
|
|||||||
"migration_complete_login" => "",
|
"migration_complete_login" => "",
|
||||||
"migration_failed" => "",
|
"migration_failed" => "",
|
||||||
"migration_error_connection" => "",
|
"migration_error_connection" => "",
|
||||||
"migration_complete_redirect" => "",
|
|
||||||
"password" => "รหัสผ่าน",
|
"password" => "รหัสผ่าน",
|
||||||
"required_username" => "จำเป็นต้องระบุชื่อผู้ใช้งาน",
|
"required_username" => "จำเป็นต้องระบุชื่อผู้ใช้งาน",
|
||||||
"username" => "ชื่อผู้ใช้",
|
"username" => "ชื่อผู้ใช้",
|
||||||
|
|||||||
@@ -1,232 +1,232 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
return [
|
return [
|
||||||
"customers_available_points" => "คะแนนที่มี",
|
'customers_available_points' => "คะแนนที่มี",
|
||||||
"rewards_package" => "คะแนนสะสม",
|
'rewards_package' => "คะแนนสะสม",
|
||||||
"rewards_remaining_balance" => "คะแนนสะสมคงเหลือ ",
|
'rewards_remaining_balance' => "คะแนนสะสมคงเหลือ ",
|
||||||
"account_number" => "บัญชี #",
|
'account_number' => "บัญชี #",
|
||||||
"add_payment" => "เพิ่มบิล",
|
'add_payment' => "เพิ่มบิล",
|
||||||
"amount_due" => "ยอดค้างชำระ",
|
'amount_due' => "ยอดค้างชำระ",
|
||||||
"amount_tendered" => "ชำระเข้ามา",
|
'amount_tendered' => "ชำระเข้ามา",
|
||||||
"authorized_signature" => "ลายเซ็นผู้มีอำนาจ",
|
'authorized_signature' => "ลายเซ็นผู้มีอำนาจ",
|
||||||
"cancel_sale" => "ยกเลิกการขาย",
|
'cancel_sale' => "ยกเลิกการขาย",
|
||||||
"cash" => "เงินสด",
|
'cash' => "เงินสด",
|
||||||
"cash_1" => "",
|
'cash_1' => "",
|
||||||
"cash_2" => "",
|
'cash_2' => "",
|
||||||
"cash_3" => "",
|
'cash_3' => "",
|
||||||
"cash_4" => "",
|
'cash_4' => "",
|
||||||
"cash_adjustment" => "การปรับเงินสดขาย",
|
'cash_adjustment' => "การปรับเงินสดขาย",
|
||||||
"cash_deposit" => "ฝากเงินสด",
|
'cash_deposit' => "ฝากเงินสด",
|
||||||
"cash_filter" => "เงินสด",
|
'cash_filter' => "เงินสด",
|
||||||
"change_due" => "เงินทอน",
|
'change_due' => "เงินทอน",
|
||||||
"change_price" => "เปลี่ยนราคาขาย",
|
'change_price' => "เปลี่ยนราคาขาย",
|
||||||
"check" => "โอนเงิน/พร้อมเพย์/เช็ค",
|
'check' => "โอนเงิน/พร้อมเพย์/เช็ค",
|
||||||
"check_balance" => "เช็คยอดคงเหลือ",
|
'check_balance' => "เช็คยอดคงเหลือ",
|
||||||
"check_filter" => "ตรวจสอบ",
|
'check_filter' => "ตรวจสอบ",
|
||||||
"close" => "",
|
'close' => "",
|
||||||
"comment" => "หมายเหตุ",
|
'comment' => "หมายเหตุ",
|
||||||
"comments" => "หมายเหตุ",
|
'comments' => "หมายเหตุ",
|
||||||
"company_name" => "",
|
'company_name' => "",
|
||||||
"complete" => "",
|
'complete' => "",
|
||||||
"complete_sale" => "จบการขาย",
|
'complete_sale' => "จบการขาย",
|
||||||
"confirm_cancel_sale" => "แน่ใจหรือไม่ที่จะล้างการขายนี้? ทุกรายการจะถูกลบทั้งหมด",
|
'confirm_cancel_sale' => "แน่ใจหรือไม่ที่จะล้างการขายนี้? ทุกรายการจะถูกลบทั้งหมด",
|
||||||
"confirm_delete" => "โปรดยืนยันการลบรายการขายที่เลือกไว้ ?",
|
'confirm_delete' => "โปรดยืนยันการลบรายการขายที่เลือกไว้ ?",
|
||||||
"confirm_restore" => "คุณแน่ใจหรือไม่ว่าต้องการยกเลิกการขายที่เลือกไว้?",
|
'confirm_restore' => "คุณแน่ใจหรือไม่ว่าต้องการยกเลิกการขายที่เลือกไว้?",
|
||||||
"credit" => "เครดิตการ์ด",
|
'credit' => "เครดิตการ์ด",
|
||||||
"credit_deposit" => "เงินฝากเครดิต",
|
'credit_deposit' => "เงินฝากเครดิต",
|
||||||
"credit_filter" => "บัตรเครติด",
|
'credit_filter' => "บัตรเครติด",
|
||||||
"current_table" => "",
|
'current_table' => "",
|
||||||
"customer" => "ลูกค้า",
|
'customer' => "ลูกค้า",
|
||||||
"customer_address" => "Customer Address",
|
'customer_address' => "Customer Address",
|
||||||
"customer_discount" => "ส่วนลด",
|
'customer_discount' => "ส่วนลด",
|
||||||
"customer_email" => "Customer Email",
|
'customer_email' => "Customer Email",
|
||||||
"customer_location" => "Customer Location",
|
'customer_location' => "Customer Location",
|
||||||
"customer_mailchimp_status" => "สถานะของระบบส่งเมล์เมล์ชิม",
|
'customer_mailchimp_status' => "สถานะของระบบส่งเมล์เมล์ชิม",
|
||||||
"customer_optional" => "(ต้องระบุวันที่ชำระเงิน)",
|
'customer_optional' => "(ต้องระบุวันที่ชำระเงิน)",
|
||||||
"customer_required" => "(ต้องระบุ)",
|
'customer_required' => "(ต้องระบุ)",
|
||||||
"customer_total" => "Total",
|
'customer_total' => "Total",
|
||||||
"customer_total_spent" => "",
|
'customer_total_spent' => "",
|
||||||
"daily_sales" => "",
|
'daily_sales' => "",
|
||||||
"date" => "วันที่ขาย",
|
'date' => "วันที่ขาย",
|
||||||
"date_range" => "ระหว่างวันที่",
|
'date_range' => "ระหว่างวันที่",
|
||||||
"date_required" => "กรุณากรอกวันที่ให้ถูกต้อง",
|
'date_required' => "กรุณากรอกวันที่ให้ถูกต้อง",
|
||||||
"date_type" => "กรุณากรอกข้อมูลในช่องวันที่",
|
'date_type' => "กรุณากรอกข้อมูลในช่องวันที่",
|
||||||
"debit" => "บัตรประชารัฐ/เดบิตการ์ด",
|
'debit' => "บัตรประชารัฐ/เดบิตการ์ด",
|
||||||
"debit_filter" => "",
|
'debit_filter' => "",
|
||||||
"delete" => "อนุญาตให้ลบ",
|
'delete' => "อนุญาตให้ลบ",
|
||||||
"delete_confirmation" => "แน่ใจหรือไม่ที่จะลบรายการขายนี้, ลบแล้วไม่สามารถเรียกกลับคืนใด้",
|
'delete_confirmation' => "แน่ใจหรือไม่ที่จะลบรายการขายนี้, ลบแล้วไม่สามารถเรียกกลับคืนใด้",
|
||||||
"delete_entire_sale" => "ลบการขายทั้งหมด",
|
'delete_entire_sale' => "ลบการขายทั้งหมด",
|
||||||
"delete_successful" => "คุณลบการขายสำเร็จ",
|
'delete_successful' => "คุณลบการขายสำเร็จ",
|
||||||
"delete_unsuccessful" => "คุณลบการขายไม่สำเร็จ",
|
'delete_unsuccessful' => "คุณลบการขายไม่สำเร็จ",
|
||||||
"description_abbrv" => "รายละเอียด",
|
'description_abbrv' => "รายละเอียด",
|
||||||
"discard" => "ยกเลิก",
|
'discard' => "ยกเลิก",
|
||||||
"discard_quote" => "",
|
'discard_quote' => "",
|
||||||
"discount" => "ส่วนลด %",
|
'discount' => "ส่วนลด %",
|
||||||
"discount_included" => "% ส่วนลด",
|
'discount_included' => "% ส่วนลด",
|
||||||
"discount_short" => "%",
|
'discount_short' => "%",
|
||||||
"due" => "วันครบกำหนด",
|
'due' => "วันครบกำหนด",
|
||||||
"due_filter" => "วันที่ครบกำหนด",
|
'due_filter' => "วันที่ครบกำหนด",
|
||||||
"edit" => "แก้ไข",
|
'edit' => "แก้ไข",
|
||||||
"edit_item" => "แก้ไขสินค้า",
|
'edit_item' => "แก้ไขสินค้า",
|
||||||
"edit_sale" => "แก้ไขการขาย",
|
'edit_sale' => "แก้ไขการขาย",
|
||||||
"email_receipt" => "อีเมลบิล",
|
'email_receipt' => "อีเมลบิล",
|
||||||
"employee" => "พนักงาน",
|
'employee' => "พนักงาน",
|
||||||
"entry" => "การนำเข้า",
|
'entry' => "การนำเข้า",
|
||||||
"error_editing_item" => "แก้ไขสินค้าล้มเหลว",
|
'error_editing_item' => "แก้ไขสินค้าล้มเหลว",
|
||||||
"negative_price_invalid" => "",
|
'negative_price_invalid' => "ราคาไม่สามารถเป็นค่าติดลบได้",
|
||||||
"negative_quantity_invalid" => "",
|
'negative_quantity_invalid' => "จำนวนไม่สามารถเป็นค่าติดลบได้",
|
||||||
"negative_discount_invalid" => "",
|
'negative_discount_invalid' => "ส่วนลดไม่สามารถเป็นค่าติดลบได้",
|
||||||
"discount_percent_exceeds_100" => "",
|
'discount_percent_exceeds_100' => "ส่วนลดเปอร์เซ็นต์มีค่าได้ไม่เกิน 100%",
|
||||||
"discount_exceeds_item_total" => "",
|
'discount_exceeds_item_total' => "ส่วนลดต้องไม่เกินจำนวนรายการขายทั้งหมด",
|
||||||
"negative_total_invalid" => "",
|
'negative_total_invalid' => "",
|
||||||
"find_or_scan_item" => "ค้นหาสินค้า",
|
'find_or_scan_item' => "ค้นหาสินค้า",
|
||||||
"find_or_scan_item_or_receipt" => "ค้นหา หรือ แสกนรายการ หรือ ใบเสร็จ",
|
'find_or_scan_item_or_receipt' => "ค้นหา หรือ แสกนรายการ หรือ ใบเสร็จ",
|
||||||
"giftcard" => "บัตรของขวัญ",
|
'giftcard' => "บัตรของขวัญ",
|
||||||
"giftcard_balance" => "ยอดคงเหลือบัตรของขวัญ",
|
'giftcard_balance' => "ยอดคงเหลือบัตรของขวัญ",
|
||||||
"giftcard_filter" => "",
|
'giftcard_filter' => "",
|
||||||
"giftcard_number" => "เลขที่บัตรของขวัญ",
|
'giftcard_number' => "เลขที่บัตรของขวัญ",
|
||||||
"group_by_category" => "กลุ่มตามหมวดหมู่",
|
'group_by_category' => "กลุ่มตามหมวดหมู่",
|
||||||
"group_by_type" => "กลุ่มตามประเภท",
|
'group_by_type' => "กลุ่มตามประเภท",
|
||||||
"hsn" => "HSN",
|
'hsn' => "HSN",
|
||||||
"id" => "เลขที่ขาย",
|
'id' => "เลขที่ขาย",
|
||||||
"include_prices" => "รวมในราคา?",
|
'include_prices' => "รวมในราคา?",
|
||||||
"invoice" => "ใบแจ้งหนี้",
|
'invoice' => "ใบแจ้งหนี้",
|
||||||
"invoice_confirm" => "ใบแจ้งหนี้นี้จะถูกส่งไปที่",
|
'invoice_confirm' => "ใบแจ้งหนี้นี้จะถูกส่งไปที่",
|
||||||
"invoice_enable" => "เลขที่ใบแจ้งหนี้",
|
'invoice_enable' => "เลขที่ใบแจ้งหนี้",
|
||||||
"invoice_filter" => "ใบแจ้งหนี้",
|
'invoice_filter' => "ใบแจ้งหนี้",
|
||||||
"invoice_no_email" => "ลูกค้ารายนี้ไม่มีที่อยู่อีเมล",
|
'invoice_no_email' => "ลูกค้ารายนี้ไม่มีที่อยู่อีเมล",
|
||||||
"invoice_number" => "เลขใบแจ้งหนี้ #",
|
'invoice_number' => "เลขใบแจ้งหนี้ #",
|
||||||
"invoice_number_duplicate" => "ใบแจ้งหนี้หมายเลข {0} จะต้องไม่ซ้ำกัน",
|
'invoice_number_duplicate' => "ใบแจ้งหนี้หมายเลข {0} จะต้องไม่ซ้ำกัน",
|
||||||
"invoice_sent" => "ส่งใบแจ้งหนี้ไปที่",
|
'invoice_sent' => "ส่งใบแจ้งหนี้ไปที่",
|
||||||
"invoice_total" => "ยอดรวมในใบแจ้งหนี้",
|
'invoice_total' => "ยอดรวมในใบแจ้งหนี้",
|
||||||
"invoice_type_custom_invoice" => "ใบแจ้งหนี้ที่กำหนดเอง (custom_invoice.php)",
|
'invoice_type_custom_invoice' => "ใบแจ้งหนี้ที่กำหนดเอง (custom_invoice.php)",
|
||||||
"invoice_type_custom_tax_invoice" => "ใบกำกับภาษีที่กำหนดเอง (custom_tax_invoice.php)",
|
'invoice_type_custom_tax_invoice' => "ใบกำกับภาษีที่กำหนดเอง (custom_tax_invoice.php)",
|
||||||
"invoice_type_invoice" => "ใบแจ้งหนี้ (invoice.php)",
|
'invoice_type_invoice' => "ใบแจ้งหนี้ (invoice.php)",
|
||||||
"invoice_type_tax_invoice" => "ใบกำกับภาษี (tax_invoice.php)",
|
'invoice_type_tax_invoice' => "ใบกำกับภาษี (tax_invoice.php)",
|
||||||
"invoice_unsent" => "ไม่สามารถส่งใบแจ้งหนี้ถึง",
|
'invoice_unsent' => "ไม่สามารถส่งใบแจ้งหนี้ถึง",
|
||||||
"invoice_update" => "คำนวณใหม่",
|
'invoice_update' => "คำนวณใหม่",
|
||||||
"item_insufficient_of_stock" => "จำนวนสินค้าไม่เพียงพอ",
|
'item_insufficient_of_stock' => "จำนวนสินค้าไม่เพียงพอ",
|
||||||
"item_name" => "ชื่อสินค้า",
|
'item_name' => "ชื่อสินค้า",
|
||||||
"item_number" => "สินค้า #",
|
'item_number' => "สินค้า #",
|
||||||
"item_out_of_stock" => "สินค้าจำหน่ายหมด",
|
'item_out_of_stock' => "สินค้าจำหน่ายหมด",
|
||||||
"key_browser" => "ความช่วยเหลือ",
|
'key_browser' => "ความช่วยเหลือ",
|
||||||
"key_cancel" => "ยกเลิกใบเสนอราคา/ใบแจ้งหนี้ /ใบการขาย นี้",
|
'key_cancel' => "ยกเลิกใบเสนอราคา/ใบแจ้งหนี้ /ใบการขาย นี้",
|
||||||
"key_customer_search" => "ค้นหาลูกค้า",
|
'key_customer_search' => "ค้นหาลูกค้า",
|
||||||
"key_finish_quote" => "จบใบเสนอราคา/ใบแจ้งหนี้โดยไม่ต้องชำระเงิน",
|
'key_finish_quote' => "จบใบเสนอราคา/ใบแจ้งหนี้โดยไม่ต้องชำระเงิน",
|
||||||
"key_finish_sale" => "เพิ่มการชำระเงินและใบแจ้งหนี้ /ใบรายการขาย",
|
'key_finish_sale' => "เพิ่มการชำระเงินและใบแจ้งหนี้ /ใบรายการขาย",
|
||||||
"key_full" => "เปิดแบบเต็มหน้าจอ",
|
'key_full' => "เปิดแบบเต็มหน้าจอ",
|
||||||
"key_function" => "ฟังก์ชั่น",
|
'key_function' => "ฟังก์ชั่น",
|
||||||
"key_help" => "คำสั่งลัดงานขาย",
|
'key_help' => "คำสั่งลัดงานขาย",
|
||||||
"key_help_modal" => "เปิดหน้าต่างคำสั่งลัดงานขาย",
|
'key_help_modal' => "เปิดหน้าต่างคำสั่งลัดงานขาย",
|
||||||
"key_in" => "ขยายเข้า",
|
'key_in' => "ขยายเข้า",
|
||||||
"key_item_search" => "ค้นหารายการขาย",
|
'key_item_search' => "ค้นหารายการขาย",
|
||||||
"key_out" => "ขยายออก",
|
'key_out' => "ขยายออก",
|
||||||
"key_payment" => "เพิ่มการชำระเงิน",
|
'key_payment' => "เพิ่มการชำระเงิน",
|
||||||
"key_print" => "พิมพ์หน้านี้",
|
'key_print' => "พิมพ์หน้านี้",
|
||||||
"key_restore" => "คืนการแสดงผลแบบดั้งเดิม/ขยาย",
|
'key_restore' => "คืนการแสดงผลแบบดั้งเดิม/ขยาย",
|
||||||
"key_search" => "ค้นหาตารางรายงาน",
|
'key_search' => "ค้นหาตารางรายงาน",
|
||||||
"key_suspend" => "พักรายการขายปัจจุบัน",
|
'key_suspend' => "พักรายการขายปัจจุบัน",
|
||||||
"key_suspended" => "แสดงรายการขายที่พักไว้",
|
'key_suspended' => "แสดงรายการขายที่พักไว้",
|
||||||
"key_system" => "ทางลัดระบบ",
|
'key_system' => "ทางลัดระบบ",
|
||||||
"key_tendered" => "แก้ไขจำนวนเงินรับมา",
|
'key_tendered' => "แก้ไขจำนวนเงินรับมา",
|
||||||
"key_title" => "ทางลัดคียบอร์ดงานขาย",
|
'key_title' => "ทางลัดคียบอร์ดงานขาย",
|
||||||
"mc" => "",
|
'mc' => "",
|
||||||
"mode" => "รูปแบบการลงทะเบียน",
|
'mode' => "รูปแบบการลงทะเบียน",
|
||||||
"must_enter_numeric" => "จำนวนที่ถุกประมูลต้องใส่ข้อมุลที่เปนตัวเลข",
|
'must_enter_numeric' => "จำนวนที่ถุกประมูลต้องใส่ข้อมุลที่เปนตัวเลข",
|
||||||
"must_enter_numeric_giftcard" => "เลขที่บัตรของขวัญ ต้องใส่ตัวเลขเท่านั้น",
|
'must_enter_numeric_giftcard' => "เลขที่บัตรของขวัญ ต้องใส่ตัวเลขเท่านั้น",
|
||||||
"new_customer" => "ลูกค้าใหม่",
|
'new_customer' => "ลูกค้าใหม่",
|
||||||
"new_item" => "สินค้าใหม่",
|
'new_item' => "สินค้าใหม่",
|
||||||
"no_description" => "ไม่ระบุรายละเอียด",
|
'no_description' => "ไม่ระบุรายละเอียด",
|
||||||
"no_filter" => "ทั้งหมด",
|
'no_filter' => "ทั้งหมด",
|
||||||
"no_items_in_cart" => "ไม่พบสินค้าในตระกร้า",
|
'no_items_in_cart' => "ไม่พบสินค้าในตระกร้า",
|
||||||
"no_sales_to_display" => "ไม่มีการขายที่จะแสดง",
|
'no_sales_to_display' => "ไม่มีการขายที่จะแสดง",
|
||||||
"none_selected" => "คุณยังไม่ได้เลือกการขายที่จะลบ",
|
'none_selected' => "คุณยังไม่ได้เลือกการขายที่จะลบ",
|
||||||
"nontaxed_ind" => " . ",
|
'nontaxed_ind' => " . ",
|
||||||
"not_authorized" => "การกระทำนี้ไม่ได้รับอนุญาต",
|
'not_authorized' => "การกระทำนี้ไม่ได้รับอนุญาต",
|
||||||
"one_or_multiple" => "การขาย",
|
'one_or_multiple' => "การขาย",
|
||||||
"payment" => "รูปแบบชำระเงิน",
|
'payment' => "รูปแบบชำระเงิน",
|
||||||
"payment_amount" => "จำนวน",
|
'payment_amount' => "จำนวน",
|
||||||
"payment_not_cover_total" => "จำนวนเงินที่ชำระต้องมากกว่าหรือเท่ากับยอดรวม",
|
'payment_not_cover_total' => "จำนวนเงินที่ชำระต้องมากกว่าหรือเท่ากับยอดรวม",
|
||||||
"payment_type" => "ชำระโดย",
|
'payment_type' => "ชำระโดย",
|
||||||
"payments" => "",
|
'payments' => "",
|
||||||
"payments_total" => "ยอดชำระแล้ว",
|
'payments_total' => "ยอดชำระแล้ว",
|
||||||
"price" => "ราคา",
|
'price' => "ราคา",
|
||||||
"print_after_sale" => "พิมพ์บิลหลังการขาย",
|
'print_after_sale' => "พิมพ์บิลหลังการขาย",
|
||||||
"quantity" => "จำนวน",
|
'quantity' => "จำนวน",
|
||||||
"quantity_less_than_reorder_level" => "คำเตือน ถ้าจำนวนของไม่เพียงพอกับความต้องการหรือไม่ตรงกับยอดในบันชี ก็สามารถทำการขายได้ แต่ต้องเชคปริมานสินค้าคงคลัง",
|
'quantity_less_than_reorder_level' => "คำเตือน ถ้าจำนวนของไม่เพียงพอกับความต้องการหรือไม่ตรงกับยอดในบันชี ก็สามารถทำการขายได้ แต่ต้องเชคปริมานสินค้าคงคลัง",
|
||||||
"quantity_less_than_zero" => "คำเตือน: ถ้าจำนวนของไม่เพียงพอกับความต้องการหรือไม่ตรงกับยอดในบัญชี ก็สามารถทำการขายได้ แต่ต้องตรวจสอบปริมาญสินค้าคงคลังก่อน",
|
'quantity_less_than_zero' => "คำเตือน: ถ้าจำนวนของไม่เพียงพอกับความต้องการหรือไม่ตรงกับยอดในบัญชี ก็สามารถทำการขายได้ แต่ต้องตรวจสอบปริมาญสินค้าคงคลังก่อน",
|
||||||
"quantity_of_items" => "ปริมาณของ {0} รายการ",
|
'quantity_of_items' => "ปริมาณของ {0} รายการ",
|
||||||
"quote" => "ใบเสนอราคา",
|
'quote' => "ใบเสนอราคา",
|
||||||
"quote_number" => "หมายเลขอ้างอิง",
|
'quote_number' => "หมายเลขอ้างอิง",
|
||||||
"quote_number_duplicate" => "หมายเลขอ้างอิงต้องไม่ซ้ำกัน",
|
'quote_number_duplicate' => "หมายเลขอ้างอิงต้องไม่ซ้ำกัน",
|
||||||
"quote_sent" => "ส่งการอ้างอิงถึง",
|
'quote_sent' => "ส่งการอ้างอิงถึง",
|
||||||
"quote_unsent" => "ส่งการอ้างอิงถึงผิดพลาด",
|
'quote_unsent' => "ส่งการอ้างอิงถึงผิดพลาด",
|
||||||
"receipt" => "บิลขาย",
|
'receipt' => "บิลขาย",
|
||||||
"receipt_no_email" => "ลูกค้านี้ไม่มีที่อยู่อีเมล์",
|
'receipt_no_email' => "ลูกค้านี้ไม่มีที่อยู่อีเมล์",
|
||||||
"receipt_number" => "จุดขาย#",
|
'receipt_number' => "จุดขาย#",
|
||||||
"receipt_sent" => "ส่งใบเสร็จไปที่",
|
'receipt_sent' => "ส่งใบเสร็จไปที่",
|
||||||
"receipt_unsent" => "ไม่สามารถส่งใบเสร็จไปที่",
|
'receipt_unsent' => "ไม่สามารถส่งใบเสร็จไปที่",
|
||||||
"refund" => "ประเภทการยกเลิกการขาย",
|
'refund' => "ประเภทการยกเลิกการขาย",
|
||||||
"register" => "ลงทะเบียนขาย",
|
'register' => "ลงทะเบียนขาย",
|
||||||
"remove_customer" => "ลบลูกค้า",
|
'remove_customer' => "ลบลูกค้า",
|
||||||
"remove_discount" => "",
|
'remove_discount' => "",
|
||||||
"return" => "คืน",
|
'return' => "คืน",
|
||||||
"rewards" => "คะแนนสะสม",
|
'rewards' => "คะแนนสะสม",
|
||||||
"rewards_balance" => "คะแนนสะสมคงเหลือ",
|
'rewards_balance' => "คะแนนสะสมคงเหลือ",
|
||||||
"sale" => "ขาย",
|
'sale' => "ขาย",
|
||||||
"sale_by_invoice" => "การขายโดยใบแจ้งหนี้",
|
'sale_by_invoice' => "การขายโดยใบแจ้งหนี้",
|
||||||
"sale_for_customer" => "ลูกค้า:",
|
'sale_for_customer' => "ลูกค้า:",
|
||||||
"sale_time" => "เวลา",
|
'sale_time' => "เวลา",
|
||||||
"sales_tax" => "ภาษีการขาย",
|
'sales_tax' => "ภาษีการขาย",
|
||||||
"sales_total" => "",
|
'sales_total' => "",
|
||||||
"select_customer" => "เลือกลูกค้า (Optional)",
|
'select_customer' => "เลือกลูกค้า (Optional)",
|
||||||
"send_invoice" => "ส่งใบแจ้งหนี้",
|
'send_invoice' => "ส่งใบแจ้งหนี้",
|
||||||
"send_quote" => "ส่งใบเสนอราคา",
|
'send_quote' => "ส่งใบเสนอราคา",
|
||||||
"send_receipt" => "ส่งใบเสร็จ",
|
'send_receipt' => "ส่งใบเสร็จ",
|
||||||
"send_work_order" => "ส่งคำสั่งงาน",
|
'send_work_order' => "ส่งคำสั่งงาน",
|
||||||
"serial" => "หมายเลขซีเรียล",
|
'serial' => "หมายเลขซีเรียล",
|
||||||
"service_charge" => "",
|
'service_charge' => "",
|
||||||
"show_due" => "",
|
'show_due' => "",
|
||||||
"show_invoice" => "ใบแจ้งหนี้",
|
'show_invoice' => "ใบแจ้งหนี้",
|
||||||
"show_receipt" => "ใบเสร็จ",
|
'show_receipt' => "ใบเสร็จ",
|
||||||
"start_typing_customer_name" => "เริ่มต้นพิมพ์ชื่อลูกค้า...",
|
'start_typing_customer_name' => "เริ่มต้นพิมพ์ชื่อลูกค้า...",
|
||||||
"start_typing_item_name" => "เริ่มต้นพิมพ์ชื่อสินค้า หรือ สแกนบาร์โค๊ด...",
|
'start_typing_item_name' => "เริ่มต้นพิมพ์ชื่อสินค้า หรือ สแกนบาร์โค๊ด...",
|
||||||
"stock" => "คลังสินค้า",
|
'stock' => "คลังสินค้า",
|
||||||
"stock_location" => "ที่เก็บ",
|
'stock_location' => "ที่เก็บ",
|
||||||
"sub_total" => "ยอดรวมย่อย",
|
'sub_total' => "ยอดรวมย่อย",
|
||||||
"successfully_deleted" => "ลบการขายสมยูรณ์",
|
'successfully_deleted' => "ลบการขายสมยูรณ์",
|
||||||
"successfully_restored" => "คุณกู้คืนสำเร็จแล้ว",
|
'successfully_restored' => "คุณกู้คืนสำเร็จแล้ว",
|
||||||
"successfully_suspended_sale" => "การขายของคุณถูกระงับเรียบร้อย",
|
'successfully_suspended_sale' => "การขายของคุณถูกระงับเรียบร้อย",
|
||||||
"successfully_updated" => "อัพเดทการขายสมบูรณ์",
|
'successfully_updated' => "อัพเดทการขายสมบูรณ์",
|
||||||
"suspend_sale" => "พักรายการ",
|
'suspend_sale' => "พักรายการ",
|
||||||
"suspended_doc_id" => "รหัสเอกสาร",
|
'suspended_doc_id' => "รหัสเอกสาร",
|
||||||
"suspended_sale_id" => "รหัสการขายที่ถูกพัก",
|
'suspended_sale_id' => "รหัสการขายที่ถูกพัก",
|
||||||
"suspended_sales" => "การขายที่พักไว้",
|
'suspended_sales' => "การขายที่พักไว้",
|
||||||
"table" => "โต๊ะ",
|
'table' => "โต๊ะ",
|
||||||
"takings" => "การขายประจำวัน",
|
'takings' => "การขายประจำวัน",
|
||||||
"tax" => "ภาษี",
|
'tax' => "ภาษี",
|
||||||
"tax_id" => "รหัสภาษี",
|
'tax_id' => "รหัสภาษี",
|
||||||
"tax_invoice" => "ใบกำกับภาษี",
|
'tax_invoice' => "ใบกำกับภาษี",
|
||||||
"tax_percent" => "ภาษี %",
|
'tax_percent' => "ภาษี %",
|
||||||
"taxed_ind" => "ภ",
|
'taxed_ind' => "ภ",
|
||||||
"total" => "ยอดรวม",
|
'total' => "ยอดรวม",
|
||||||
"total_tax_exclusive" => "ยอดไม่รวมภาษี",
|
'total_tax_exclusive' => "ยอดไม่รวมภาษี",
|
||||||
"transaction_failed" => "การดำเนินการขายล้มเหลว",
|
'transaction_failed' => "การดำเนินการขายล้มเหลว",
|
||||||
"unable_to_add_item" => "เพิ่มรายการไปยังการขายล้มเหลว",
|
'unable_to_add_item' => "เพิ่มรายการไปยังการขายล้มเหลว",
|
||||||
"unsuccessfully_deleted" => "ลบการขายไม่สำเร็จ",
|
'unsuccessfully_deleted' => "ลบการขายไม่สำเร็จ",
|
||||||
"unsuccessfully_restored" => "การคืนค่ารายการขายล้มเหลว",
|
'unsuccessfully_restored' => "การคืนค่ารายการขายล้มเหลว",
|
||||||
"unsuccessfully_suspended_sale" => "การขายของคุณถูกระงับเรียบร้อย",
|
'unsuccessfully_suspended_sale' => "การขายของคุณถูกระงับเรียบร้อย",
|
||||||
"unsuccessfully_updated" => "อัพเดทการขายไม่สมบูรณ์",
|
'unsuccessfully_updated' => "อัพเดทการขายไม่สมบูรณ์",
|
||||||
"unsuspend" => "ยกเลิกการระงับ",
|
'unsuspend' => "ยกเลิกการระงับ",
|
||||||
"unsuspend_and_delete" => "ยกเลิกการระงับ และ ลบ",
|
'unsuspend_and_delete' => "ยกเลิกการระงับ และ ลบ",
|
||||||
"update" => "แก้ไข",
|
'update' => "แก้ไข",
|
||||||
"upi" => "ยูพีไอ",
|
'upi' => "ยูพีไอ",
|
||||||
"visa" => "",
|
'visa' => "",
|
||||||
"wholesale" => "",
|
'wholesale' => "",
|
||||||
"work_order" => "คำสั่งงาน",
|
'work_order' => "คำสั่งงาน",
|
||||||
"work_order_number" => "หมายเลขคำสั่งงาน",
|
'work_order_number' => "หมายเลขคำสั่งงาน",
|
||||||
"work_order_number_duplicate" => "หมายเลขคำสั่งงานต้องไม่ซ้ำกัน",
|
'work_order_number_duplicate' => "หมายเลขคำสั่งงานต้องไม่ซ้ำกัน",
|
||||||
"work_order_sent" => "คำสั่งงานส่งถึง",
|
'work_order_sent' => "คำสั่งงานส่งถึง",
|
||||||
"work_order_unsent" => "ส่งคำสั่งงานล้มเหลว",
|
'work_order_unsent' => "ส่งคำสั่งงานล้มเหลว",
|
||||||
"selected_customer" => "ลูกค้าที่เลือก",
|
'selected_customer' => "ลูกค้าที่เลือก",
|
||||||
];
|
];
|
||||||
|
|||||||
@@ -82,4 +82,40 @@ class Email_lib
|
|||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Gets the mime type of the company logo file.
|
||||||
|
*
|
||||||
|
* @return string Mime type or empty string if logo doesn't exist
|
||||||
|
*/
|
||||||
|
public function getLogoMimeType(): string
|
||||||
|
{
|
||||||
|
$logo_path = FCPATH . 'uploads/' . $this->config['company_logo'];
|
||||||
|
|
||||||
|
if (!empty($this->config['company_logo']) && file_exists($logo_path)) {
|
||||||
|
$mimeType = mime_content_type($logo_path);
|
||||||
|
return $mimeType !== false ? $mimeType : '';
|
||||||
|
}
|
||||||
|
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Builds an img tag for the company logo to use in email templates.
|
||||||
|
*
|
||||||
|
* @return string HTML img tag with base64-encoded logo, or empty string if no logo
|
||||||
|
*/
|
||||||
|
public function buildLogoImgTag(): string
|
||||||
|
{
|
||||||
|
$mimeType = $this->getLogoMimeType();
|
||||||
|
|
||||||
|
if ($mimeType === '') {
|
||||||
|
return '';
|
||||||
|
}
|
||||||
|
|
||||||
|
$logo_path = FCPATH . 'uploads/' . $this->config['company_logo'];
|
||||||
|
$logo_data = base64_encode(file_get_contents($logo_path));
|
||||||
|
|
||||||
|
return '<img id="image" src="data:' . $mimeType . ';base64,' . $logo_data . '" alt="company_logo">';
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -2,7 +2,6 @@
|
|||||||
|
|
||||||
namespace App\Libraries;
|
namespace App\Libraries;
|
||||||
|
|
||||||
use CodeIgniter\Database\Exceptions\DatabaseException;
|
|
||||||
use CodeIgniter\Database\MigrationRunner;
|
use CodeIgniter\Database\MigrationRunner;
|
||||||
use Config\Database;
|
use Config\Database;
|
||||||
use stdClass;
|
use stdClass;
|
||||||
@@ -26,7 +25,7 @@ class MY_Migration extends MigrationRunner
|
|||||||
public function get_latest_migration(): int
|
public function get_latest_migration(): int
|
||||||
{
|
{
|
||||||
$migrations = $this->findMigrations();
|
$migrations = $this->findMigrations();
|
||||||
return basename(end($migrations)->version);
|
return (int) basename(end($migrations)->version);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
@@ -42,9 +41,11 @@ class MY_Migration extends MigrationRunner
|
|||||||
$builder = $db->table('migrations');
|
$builder = $db->table('migrations');
|
||||||
$builder->select('version')->orderBy('version', 'DESC')->limit(1);
|
$builder->select('version')->orderBy('version', 'DESC')->limit(1);
|
||||||
$result = $builder->get()->getRow();
|
$result = $builder->get()->getRow();
|
||||||
return $result ? $result->version : 0;
|
return $result ? (int) $result->version : 0;
|
||||||
}
|
}
|
||||||
} catch (DatabaseException $e) {
|
} catch (\Exception $e) {
|
||||||
|
// Database not available yet (e.g. fresh install before schema).
|
||||||
|
// Catches mysqli_sql_exception which is not a DatabaseException.
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -76,8 +77,9 @@ class MY_Migration extends MigrationRunner
|
|||||||
$result = $builder->get()->getRow();
|
$result = $builder->get()->getRow();
|
||||||
return $result ? $result->version : false;
|
return $result ? $result->version : false;
|
||||||
}
|
}
|
||||||
} catch (DatabaseException $e) {
|
} catch (\Exception $e) {
|
||||||
// Database doesn't exist yet or connection failed
|
// Database not available yet (e.g. fresh install before schema).
|
||||||
|
// Catches mysqli_sql_exception which is not a DatabaseException.
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
|
|||||||
@@ -23,6 +23,19 @@ use ReflectionException;
|
|||||||
*/
|
*/
|
||||||
class Sale_lib
|
class Sale_lib
|
||||||
{
|
{
|
||||||
|
private const KEY_SHORTCUT_DEFAULTS = [
|
||||||
|
'cancel' => ['value' => '27 | ESC', 'code' => 27, 'label' => 'ESC'],
|
||||||
|
'items' => ['value' => '49 | ALT + 1', 'code' => 49, 'label' => 'ALT + 1'],
|
||||||
|
'customers' => ['value' => '50 | ALT + 2', 'code' => 50, 'label' => 'ALT + 2'],
|
||||||
|
'suspend' => ['value' => '51 | ALT + 3', 'code' => 51, 'label' => 'ALT + 3'],
|
||||||
|
'suspended' => ['value' => '52 | ALT + 4', 'code' => 52, 'label' => 'ALT + 4'],
|
||||||
|
'amount' => ['value' => '53 | ALT + 5', 'code' => 53, 'label' => 'ALT + 5'],
|
||||||
|
'payment' => ['value' => '54 | ALT + 6', 'code' => 54, 'label' => 'ALT + 6'],
|
||||||
|
'complete' => ['value' => '55 | ALT + 7', 'code' => 55, 'label' => 'ALT + 7'],
|
||||||
|
'finish' => ['value' => '56 | ALT + 8', 'code' => 56, 'label' => 'ALT + 8'],
|
||||||
|
'help' => ['value' => '57 | ALT + 9', 'code' => 57, 'label' => 'ALT + 9'],
|
||||||
|
];
|
||||||
|
|
||||||
private Attribute $attribute;
|
private Attribute $attribute;
|
||||||
private Customer $customer;
|
private Customer $customer;
|
||||||
private Dinner_table $dinner_table;
|
private Dinner_table $dinner_table;
|
||||||
@@ -95,6 +108,11 @@ class Sale_lib
|
|||||||
'custom_tax_invoice'
|
'custom_tax_invoice'
|
||||||
];
|
];
|
||||||
|
|
||||||
|
private const ALLOWED_RECEIPT_TEMPLATES = [
|
||||||
|
'receipt_default',
|
||||||
|
'receipt_short'
|
||||||
|
];
|
||||||
|
|
||||||
public function get_invoice_type_options(): array
|
public function get_invoice_type_options(): array
|
||||||
{
|
{
|
||||||
$invoice_types = [];
|
$invoice_types = [];
|
||||||
@@ -105,11 +123,54 @@ class Sale_lib
|
|||||||
return $invoice_types;
|
return $invoice_types;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns the available keyboard shortcut choices for the configuration screen.
|
||||||
|
*
|
||||||
|
* @return array<string, string>
|
||||||
|
*/
|
||||||
|
public function getKeyShortcutsOptions(): array
|
||||||
|
{
|
||||||
|
$keyShortcuts = [];
|
||||||
|
|
||||||
|
foreach (self::KEY_SHORTCUT_DEFAULTS as $shortcut) {
|
||||||
|
$keyShortcuts[$shortcut['value']] = $shortcut['label'];
|
||||||
|
}
|
||||||
|
|
||||||
|
return $keyShortcuts;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Returns parsed shortcut bindings from app_config with sensible defaults.
|
||||||
|
*
|
||||||
|
* @return array<string, array{value:string,code:int,label:string}>
|
||||||
|
*/
|
||||||
|
public function getKeyShortcuts(): array
|
||||||
|
{
|
||||||
|
$keyboardShortcuts = [];
|
||||||
|
|
||||||
|
foreach (self::KEY_SHORTCUT_DEFAULTS as $name => $default) {
|
||||||
|
$value = $this->config["key_$name"] ?? $default['value'];
|
||||||
|
$parts = array_map('trim', explode('|', $value, 2));
|
||||||
|
$keyboardShortcuts[$name] = [
|
||||||
|
'value' => $value,
|
||||||
|
'code' => (int)($parts[0] ?? $default['code']),
|
||||||
|
'label' => $parts[1] ?? $default['label']
|
||||||
|
];
|
||||||
|
}
|
||||||
|
|
||||||
|
return $keyboardShortcuts;
|
||||||
|
}
|
||||||
|
|
||||||
public static function isValidInvoiceType(string $invoice_type): bool
|
public static function isValidInvoiceType(string $invoice_type): bool
|
||||||
{
|
{
|
||||||
return in_array($invoice_type, self::ALLOWED_INVOICE_TYPES, true);
|
return in_array($invoice_type, self::ALLOWED_INVOICE_TYPES, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public static function isValidReceiptTemplate(string $receipt_template): bool
|
||||||
|
{
|
||||||
|
return in_array($receipt_template, self::ALLOWED_RECEIPT_TEMPLATES, true);
|
||||||
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return array
|
* @return array
|
||||||
*/
|
*/
|
||||||
|
|||||||
@@ -601,6 +601,10 @@ class Attribute extends Model
|
|||||||
*/
|
*/
|
||||||
public function saveAttributeLink(int $itemId, int $definitionId, int $attributeId): bool
|
public function saveAttributeLink(int $itemId, int $definitionId, int $attributeId): bool
|
||||||
{
|
{
|
||||||
|
if ($attributeId <= 0) {
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
$normalizedItemId = empty($itemId) ? null : $itemId;
|
$normalizedItemId = empty($itemId) ? null : $itemId;
|
||||||
$normalizedAttributeId = empty($attributeId) ? null : $attributeId;
|
$normalizedAttributeId = empty($attributeId) ? null : $attributeId;
|
||||||
|
|
||||||
|
|||||||
@@ -65,8 +65,10 @@ class Item extends Model
|
|||||||
public function exists(string $item_id, bool $ignore_deleted = false, bool $deleted = false): bool
|
public function exists(string $item_id, bool $ignore_deleted = false, bool $deleted = false): bool
|
||||||
{
|
{
|
||||||
$builder = $this->db->table('items');
|
$builder = $this->db->table('items');
|
||||||
|
$builder->groupStart();
|
||||||
$builder->where('item_id', $item_id);
|
$builder->where('item_id', $item_id);
|
||||||
$builder->orWhere('item_number', $item_id);
|
$builder->orWhere('item_number', $item_id);
|
||||||
|
$builder->groupEnd();
|
||||||
|
|
||||||
if (!$ignore_deleted) {
|
if (!$ignore_deleted) {
|
||||||
$builder->where('deleted', $deleted);
|
$builder->where('deleted', $deleted);
|
||||||
@@ -389,9 +391,10 @@ class Item extends Model
|
|||||||
public function get_item_id(string $item_number, bool $ignore_deleted = false, bool $deleted = false): bool|int
|
public function get_item_id(string $item_number, bool $ignore_deleted = false, bool $deleted = false): bool|int
|
||||||
{
|
{
|
||||||
$builder = $this->db->table('items');
|
$builder = $this->db->table('items');
|
||||||
$builder->join('suppliers', 'suppliers.person_id = items.supplier_id', 'left');
|
$builder->groupStart();
|
||||||
$builder->where('item_number', $item_number);
|
$builder->where('item_number', $item_number);
|
||||||
$builder->orWhere('item_id', $item_number);
|
$builder->orWhere('item_id', $item_number);
|
||||||
|
$builder->groupEnd();
|
||||||
|
|
||||||
if (!$ignore_deleted) {
|
if (!$ignore_deleted) {
|
||||||
$builder->where('items.deleted', $deleted);
|
$builder->where('items.deleted', $deleted);
|
||||||
|
|||||||
@@ -294,7 +294,9 @@ class Receiving extends Model
|
|||||||
lang('Sales.check') => lang('Sales.check'),
|
lang('Sales.check') => lang('Sales.check'),
|
||||||
lang('Sales.debit') => lang('Sales.debit'),
|
lang('Sales.debit') => lang('Sales.debit'),
|
||||||
lang('Sales.credit') => lang('Sales.credit'),
|
lang('Sales.credit') => lang('Sales.credit'),
|
||||||
lang('Sales.due') => lang('Sales.due')
|
lang('Sales.due') => lang('Sales.due'),
|
||||||
|
lang('Sales.bank_transfer') => lang('Sales.bank_transfer'),
|
||||||
|
lang('Sales.wallet') => lang('Sales.wallet')
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|||||||
@@ -33,14 +33,16 @@ class Summary_sales_taxes extends Summary_report
|
|||||||
* @param object $builder
|
* @param object $builder
|
||||||
* @return void
|
* @return void
|
||||||
*/
|
*/
|
||||||
protected function _where(array $inputs, object &$builder): void // TODO: hungarian notation
|
protected function _where(array $inputs, object &$builder): void
|
||||||
{
|
{
|
||||||
$builder->where('sales.sale_status', COMPLETED);
|
$builder->where('sales.sale_status', COMPLETED);
|
||||||
|
|
||||||
if (empty($this->config['date_or_time_format'])) { // TODO: Duplicated code
|
if (empty($this->config['date_or_time_format'])) {
|
||||||
$builder->where('DATE(sales.sale_time) BETWEEN ' . $this->db->escape($inputs['start_date']) . ' AND ' . $this->db->escape($inputs['end_date']));
|
$builder->where('DATE(sales.sale_time) >=', $inputs['start_date']);
|
||||||
|
$builder->where('DATE(sales.sale_time) <=', $inputs['end_date']);
|
||||||
} else {
|
} else {
|
||||||
$builder->where('sales.sale_time BETWEEN ' . $this->db->escape(rawurldecode($inputs['start_date'])) . ' AND ' . $this->db->escape(rawurldecode($inputs['end_date'])));
|
$builder->where('sales.sale_time >=', $inputs['start_date']);
|
||||||
|
$builder->where('sales.sale_time <=', $inputs['end_date']);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -53,9 +55,11 @@ class Summary_sales_taxes extends Summary_report
|
|||||||
$builder = $this->db->table('sales_taxes');
|
$builder = $this->db->table('sales_taxes');
|
||||||
|
|
||||||
if (empty($this->config['date_or_time_format'])) {
|
if (empty($this->config['date_or_time_format'])) {
|
||||||
$builder->where('DATE(sale_time) BETWEEN ' . $inputs['start_date'] . ' AND ' . $inputs['end_date']);
|
$builder->where('DATE(sale_time) >=', $inputs['start_date']);
|
||||||
|
$builder->where('DATE(sale_time) <=', $inputs['end_date']);
|
||||||
} else {
|
} else {
|
||||||
$builder->where('sale_time BETWEEN ' . $this->db->escape(rawurldecode($inputs['start_date'])) . ' AND ' . $this->db->escape(rawurldecode($inputs['end_date'])));
|
$builder->where('sale_time >=', $inputs['start_date']);
|
||||||
|
$builder->where('sale_time <=', $inputs['end_date']);
|
||||||
}
|
}
|
||||||
|
|
||||||
$builder->select('reporting_authority, jurisdiction_name, tax_category, tax_rate, SUM(sale_tax_amount) AS tax');
|
$builder->select('reporting_authority, jurisdiction_name, tax_category, tax_rate, SUM(sale_tax_amount) AS tax');
|
||||||
|
|||||||
@@ -277,6 +277,14 @@ class Sale extends Model
|
|||||||
$builder->like('payment_type', lang('Sales.debit'));
|
$builder->like('payment_type', lang('Sales.debit'));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($filters['only_bank_transfer']) {
|
||||||
|
$builder->like('payment_type', lang('Sales.bank_transfer'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($filters['only_wallet']) {
|
||||||
|
$builder->like('payment_type', lang('Sales.wallet'));
|
||||||
|
}
|
||||||
|
|
||||||
$builder->groupBy('payment_type');
|
$builder->groupBy('payment_type');
|
||||||
|
|
||||||
$payments = $builder->get()->getResultArray();
|
$payments = $builder->get()->getResultArray();
|
||||||
@@ -319,7 +327,7 @@ class Sale extends Model
|
|||||||
{
|
{
|
||||||
$suggestions = [];
|
$suggestions = [];
|
||||||
|
|
||||||
if (!$this->is_valid_receipt($search)) {
|
if (!$this->isValidReceipt($search)) {
|
||||||
$builder = $this->db->table('sales');
|
$builder = $this->db->table('sales');
|
||||||
$builder->distinct()->select('first_name, last_name');
|
$builder->distinct()->select('first_name, last_name');
|
||||||
$builder->join('people', 'people.person_id = sales.customer_id');
|
$builder->join('people', 'people.person_id = sales.customer_id');
|
||||||
@@ -400,21 +408,21 @@ class Sale extends Model
|
|||||||
/**
|
/**
|
||||||
* Checks if valid receipt
|
* Checks if valid receipt
|
||||||
*/
|
*/
|
||||||
public function is_valid_receipt(string|null &$receipt_sale_id): bool // TODO: like the others, maybe this should be an array rather than a delimited string... either that or the parameter name needs to be changed. $receipt_sale_id implies that it's an int.
|
public function isValidReceipt(string|null &$receiptSaleId): bool // TODO: like the others, maybe this should be an array rather than a delimited string... either that or the parameter name needs to be changed. $receipt_sale_id implies that it's an int.
|
||||||
{
|
{
|
||||||
$config = config(OSPOS::class)->settings;
|
$config = config(OSPOS::class)->settings;
|
||||||
|
|
||||||
if (!empty($receipt_sale_id)) {
|
if (!empty($receiptSaleId)) {
|
||||||
// POS #
|
// POS #
|
||||||
$pieces = explode(' ', $receipt_sale_id);
|
$pieces = explode(' ', trim($receiptSaleId));
|
||||||
|
|
||||||
if (count($pieces) == 2 && preg_match('/(POS)/i', $pieces[0])) {
|
if (count($pieces) == 2 && strtoupper($pieces[0]) === 'POS' && ctype_digit($pieces[1])) {
|
||||||
return $this->exists($pieces[1]);
|
return $this->exists((int)$pieces[1]);
|
||||||
} elseif ($config['invoice_enable']) {
|
} elseif ($config['invoice_enable']) {
|
||||||
$sale_info = $this->get_sale_by_invoice_number($receipt_sale_id);
|
$saleInfo = $this->get_sale_by_invoice_number($receiptSaleId);
|
||||||
|
|
||||||
if ($sale_info->getNumRows() > 0) {
|
if ($saleInfo->getNumRows() > 0) {
|
||||||
$receipt_sale_id = 'POS ' . $sale_info->getRow()->sale_id;
|
$receiptSaleId = 'POS ' . $saleInfo->getRow()->sale_id;
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@@ -1509,5 +1517,13 @@ class Sale extends Model
|
|||||||
if ($filters['only_check']) {
|
if ($filters['only_check']) {
|
||||||
$builder->like('payments.payment_type', lang('Sales.check'));
|
$builder->like('payments.payment_type', lang('Sales.check'));
|
||||||
}
|
}
|
||||||
|
|
||||||
|
if ($filters['only_bank_transfer']) {
|
||||||
|
$builder->like('payments.payment_type', lang('Sales.bank_transfer'));
|
||||||
|
}
|
||||||
|
|
||||||
|
if ($filters['only_wallet']) {
|
||||||
|
$builder->like('payments.payment_type', lang('Sales.wallet'));
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|||||||
@@ -10,93 +10,75 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("attributes/saveDefinition/$definition_id", ['id' => 'attribute_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("attributes/saveDefinition/$definition_id", ['id' => 'attribute_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="attribute_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="definition_name" class="form-label"><?= lang('Attributes.definition_name'); ?></label>
|
||||||
<?= form_label(lang('Attributes.definition_name'), 'definition_name', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="definition_name-icon"><i class="bi bi-star"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="definition_name" id="definition_name" aria-describedby="definition_name-icon" value="<?= esc($definition_info->definition_name); ?>">
|
||||||
'name' => 'definition_name',
|
</div>
|
||||||
'id' => 'definition_name',
|
|
||||||
'class' => 'form-control input-sm',
|
<label for="definition_type" class="form-label"><?= lang('Attributes.definition_type'); ?></label>
|
||||||
'value' => esc($definition_info->definition_name)
|
<div class="input-group mb-3">
|
||||||
]) ?>
|
<span class="input-group-text" id="definition_type-icon"><i class="bi bi-list"></i></span>
|
||||||
</div>
|
<select class="form-select" name="definition_type" id="definition_type" aria-describedby="definition_type-icon">
|
||||||
|
<?php foreach (DEFINITION_TYPES as $key => $label): ?>
|
||||||
|
<option value="<?= $key ?>" <?= ($key === array_search($definition_info->definition_type, DEFINITION_TYPES)) ? 'selected' : '' ?>>
|
||||||
|
<?= $label ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="definition_group" class="form-label"><?= lang('Attributes.definition_group'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="definition_group-icon"><i class="bi bi-collection"></i></span>
|
||||||
|
<select class="form-select" name="definition_group" id="definition_group" aria-describedby="definition_group-icon" <?= empty($definition_group) ? 'disabled' : '' ?>>
|
||||||
|
<?php foreach ($definition_group as $key => $label): ?>
|
||||||
|
<option value="<?= $key ?>" <?= ($key == $definition_info->definition_fk) ? 'selected' : '' ?>>
|
||||||
|
<?= $label ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="toggle-hide d-none">
|
||||||
|
<label for="definition_flags" class="form-label"><?= lang('Attributes.definition_flags'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="definition_flags-icon"><i class="bi bi-eyeglasses"></i></span>
|
||||||
|
<select class="form-select" name="definition_flags[]" id="definition_flags" aria-describedby="definition_flags-icon" multiple>
|
||||||
|
<?php foreach ($definition_flags as $key => $label): ?>
|
||||||
|
<option value="<?= $key ?>" <?= in_array($key, array_keys($selected_definition_flags)) ? 'selected' : '' ?>>
|
||||||
|
<?= $label ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="toggle-hide d-none">
|
||||||
<?= form_label(lang('Attributes.definition_type'), 'definition_type', ['class' => 'required control-label col-xs-3']) ?>
|
<label for="definition_unit" class="form-label"><?= lang('Attributes.definition_unit'); ?></label>
|
||||||
<div class="col-xs-8">
|
<div class="input-group mb-3">
|
||||||
<?= form_dropdown('definition_type', DEFINITION_TYPES, array_search($definition_info->definition_type, DEFINITION_TYPES), 'id="definition_type" class="form-control"') ?>
|
<span class="input-group-text" id="definition_unit-icon"><i class="bi bi-flask"></i></span>
|
||||||
</div>
|
<input type="text" class="form-control" name="definition_unit" id="definition_unit" aria-describedby="definition_unit-icon" value="<?= esc($definition_info->definition_unit); ?>">
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="toggle-hide d-none">
|
||||||
<?= form_label(lang('Attributes.definition_group'), 'definition_group', ['class' => 'control-label col-xs-3']) ?>
|
<label for="definition_value" class="form-label"><?= lang('Attributes.definition_values'); ?></label>
|
||||||
<div class="col-xs-8">
|
<div class="input-group mb-3">
|
||||||
<?= form_dropdown(
|
<span class="input-group-text" id="definition_value-icon"><i class="bi bi-list"></i></span>
|
||||||
'definition_group',
|
<input type="text" class="form-control" name="definition_value" id="definition_value" aria-describedby="definition_value-icon">
|
||||||
$definition_group,
|
<button type="button" class="btn btn-outline-secondary" id="add_attribute_value"><i class="bi bi-plus-circle"></i></button>
|
||||||
$definition_info->definition_fk,
|
|
||||||
'id="definition_group" class="form-control" ' . (empty($definition_group) ? 'disabled="disabled"' : '')
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm hidden">
|
<div class="toggle-hide d-none">
|
||||||
<?= form_label(lang('Attributes.definition_flags'), 'definition_flags', ['class' => 'control-label col-xs-3']) ?>
|
<ul class="list-group" id="definition_list_group"></ul>
|
||||||
<div class="col-xs-8">
|
</div>
|
||||||
<div class="input-group">
|
|
||||||
<?= form_multiselect('definition_flags[]', $definition_flags, array_keys($selected_definition_flags), [
|
|
||||||
'id' => 'definition_flags',
|
|
||||||
'class' => 'selectpicker show-menu-arrow',
|
|
||||||
'data-none-selected-text' => lang('Common.none_selected_text'),
|
|
||||||
'data-selected-text-format' => 'count > 1',
|
|
||||||
'data-style' => 'btn-default btn-sm',
|
|
||||||
'data-width' => 'fit'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm hidden">
|
|
||||||
<?= form_label(lang('Attributes.definition_unit'), 'definition_units', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'definition_unit',
|
|
||||||
'value' => esc($definition_info->definition_unit),
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'id' => 'definition_unit'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm hidden">
|
|
||||||
<?= form_label(lang('Attributes.definition_values'), 'definition_value', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input(['name' => 'definition_value', 'class' => 'form-control input-sm', 'id' => 'definition_value']) ?>
|
|
||||||
<span id="add_attribute_value" class="input-group-addon input-sm btn btn-default">
|
|
||||||
<span class="glyphicon glyphicon-plus-sign"></span>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm hidden">
|
|
||||||
<?= form_label(' ', 'definition_list_group', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<ul id="definition_list_group" class="list-group"></ul>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -125,8 +107,8 @@
|
|||||||
if (definition_id == -1) {
|
if (definition_id == -1) {
|
||||||
$('#definition_name').prop("disabled", true);
|
$('#definition_name').prop("disabled", true);
|
||||||
$('#definition_type').prop("disabled", true);
|
$('#definition_type').prop("disabled", true);
|
||||||
$('#definition_group').parents('.form-group').toggleClass("hidden", true);
|
$('#definition_group').parents('.toggle-hide').toggleClass("d-none", true);
|
||||||
$('#definition_flags').parents('.form-group').toggleClass('hidden', true);
|
$('#definition_flags').parents('.toggle-hide').toggleClass("d-none", true);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
disable_category_dropdown();
|
disable_category_dropdown();
|
||||||
@@ -137,21 +119,23 @@
|
|||||||
var is_no_group = $('#definition_type').val() !== '0';
|
var is_no_group = $('#definition_type').val() !== '0';
|
||||||
var is_category_dropdown = definition_id == -1;
|
var is_category_dropdown = definition_id == -1;
|
||||||
|
|
||||||
$('#definition_value, #definition_list_group').parents('.form-group').toggleClass('hidden', is_dropdown);
|
$('#definition_value, #definition_list_group').parents('.toggle-hide').toggleClass('d-none', is_dropdown);
|
||||||
$('#definition_unit').parents('.form-group').toggleClass('hidden', is_decimal);
|
$('#definition_unit').parents('.toggle-hide').toggleClass('d-none', is_decimal);
|
||||||
|
|
||||||
// Appropriately show definition flags if not category_dropdown
|
// Appropriately show definition flags if not category_dropdown
|
||||||
if (definition_id != -1) {
|
if (definition_id != -1) {
|
||||||
$('#definition_flags').parents('.form-group').toggleClass('hidden', !is_no_group);
|
$('#definition_flags').parents('.toggle-hide').toggleClass('d-none', !is_no_group);
|
||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
$('#definition_type').change(show_hide_fields);
|
$('#definition_type').change(show_hide_fields);
|
||||||
show_hide_fields();
|
show_hide_fields();
|
||||||
|
|
||||||
$('.selectpicker').each(function() {
|
new TomSelect('#definition_flags', {
|
||||||
var $selectpicker = $(this);
|
plugins: ['checkbox_options', 'remove_button'],
|
||||||
$.fn.selectpicker.call($selectpicker, $selectpicker.data());
|
placeholder: '<?= lang('Common.none_selected_text') ?>',
|
||||||
|
hidePlaceholder: true,
|
||||||
|
closeAfterSelect: false,
|
||||||
});
|
});
|
||||||
|
|
||||||
var remove_attribute_value = function() {
|
var remove_attribute_value = function() {
|
||||||
@@ -192,7 +176,7 @@
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$('#definition_list_group').append('<li class="list-group-item">' + DOMPurify.sanitize(value) + '<a href="javascript:void(0);"><span class="glyphicon glyphicon-trash pull-right"></span></a></li>')
|
$('#definition_list_group').append('<li class="list-group-item list-group-item-action d-flex justify-content-between">' + DOMPurify.sanitize(value) + '<a href="javascript:void(0);"><span class="text-danger"><i class="bi bi-trash"></i></span></a></li>')
|
||||||
.find(':last-child a').click(remove_attribute_value);
|
.find(':last-child a').click(remove_attribute_value);
|
||||||
$('#definition_value').val('');
|
$('#definition_value').val('');
|
||||||
};
|
};
|
||||||
|
|||||||
@@ -7,96 +7,98 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="definition_name" class="form-label"><?= lang('Attributes.definition_name'); ?></label>
|
||||||
<?= form_label(lang('Attributes.definition_name'), 'definition_name_label', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text"><i class="bi bi-star"></i></span>
|
||||||
<?= form_dropdown([
|
<select class="form-select" name="definition_name" id="definition_name">
|
||||||
'name' => 'definition_name',
|
<option value="-1" selected></option>
|
||||||
'options' => $definition_names,
|
<?php foreach ($definition_names as $key => $value): ?>
|
||||||
'selected' => -1,
|
<option value="<?= $key ?>"><?= $value ?></option>
|
||||||
'class' => 'form-control',
|
<?php endforeach; ?>
|
||||||
'id' => 'definition_name'
|
</select>
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<?php foreach ($definition_values as $definition_id => $definition_value) { ?>
|
<?php foreach ($definition_values as $definition_id => $definition_value) { ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<span class="attribute_added">
|
||||||
<?= form_label(esc($definition_value['definition_name']), esc($definition_value['definition_name']), ['class' => 'control-label col-xs-3']) ?>
|
<?php
|
||||||
<div class="col-xs-8">
|
$attribute_value = $definition_value['attribute_value'];
|
||||||
<div class="input-group">
|
|
||||||
<?php
|
|
||||||
echo form_hidden("attribute_ids[$definition_id]", strval($definition_value['attribute_id']));
|
|
||||||
$attribute_value = $definition_value['attribute_value'];
|
|
||||||
|
|
||||||
switch ($definition_value['definition_type']) {
|
switch ($definition_value['definition_type']) {
|
||||||
case DATE:
|
|
||||||
$value = (empty($attribute_value) || empty($attribute_value->attribute_date)) ? NOW : strtotime($attribute_value->attribute_date);
|
|
||||||
echo form_input([
|
|
||||||
'name' => "attribute_links[$definition_id]",
|
|
||||||
'value' => to_date($value),
|
|
||||||
'class' => 'form-control input-sm datetime',
|
|
||||||
'data-definition-id' => $definition_id,
|
|
||||||
'readonly' => 'true'
|
|
||||||
]);
|
|
||||||
break;
|
|
||||||
case DROPDOWN:
|
|
||||||
$selected_value = $definition_value['selected_value'];
|
|
||||||
echo form_dropdown([
|
|
||||||
'name' => "attribute_links[$definition_id]",
|
|
||||||
'options' => $definition_value['values'],
|
|
||||||
'selected' => $selected_value,
|
|
||||||
'class' => 'form-control',
|
|
||||||
'data-definition-id' => $definition_id
|
|
||||||
]);
|
|
||||||
break;
|
|
||||||
case TEXT:
|
|
||||||
$value = (empty($attribute_value) || empty($attribute_value->attribute_value)) ? $definition_value['selected_value'] : $attribute_value->attribute_value;
|
|
||||||
echo form_input([
|
|
||||||
'name' => "attribute_links[$definition_id]",
|
|
||||||
'value' => esc($value),
|
|
||||||
'class' => 'form-control valid_chars',
|
|
||||||
'data-definition-id' => $definition_id
|
|
||||||
]);
|
|
||||||
break;
|
|
||||||
case DECIMAL:
|
|
||||||
$value = (empty($attribute_value) || empty($attribute_value->attribute_decimal)) ? $definition_value['selected_value'] : $attribute_value->attribute_decimal;
|
|
||||||
echo form_input([
|
|
||||||
'name' => "attribute_links[$definition_id]",
|
|
||||||
'value' => to_decimals((float)$value),
|
|
||||||
'class' => 'form-control valid_chars',
|
|
||||||
'data-definition-id' => $definition_id
|
|
||||||
]);
|
|
||||||
break;
|
|
||||||
case CHECKBOX:
|
|
||||||
$value = (empty($attribute_value) || empty($attribute_value->attribute_value)) ? $definition_value['selected_value'] : $attribute_value->attribute_value;
|
|
||||||
|
|
||||||
// Sends 0 if the box is unchecked instead of not sending anything.
|
case DATE:
|
||||||
echo form_input([
|
$value = (empty($attribute_value) || empty($attribute_value->attribute_date)) ? NOW : strtotime($attribute_value->attribute_date);
|
||||||
'type' => 'hidden',
|
?>
|
||||||
'name' => "attribute_links[$definition_id]",
|
<label for="attribute_links[<?= $definition_id ?>]" class="form-label"><?= esc($definition_value['definition_name']) ?></label>
|
||||||
'id' => "attribute_links[$definition_id]",
|
<div class="input-group mb-3">
|
||||||
'value' => 0,
|
<span class="input-group-text" id="attribute_links[<?= $definition_id ?>]-icon"><i class="bi bi-calendar2"></i></span>
|
||||||
'data-definition-id' => $definition_id
|
<input type="hidden" name="attribute_ids[<?= $definition_id ?>]" value="<?= strval($definition_value['attribute_id']) ?>">
|
||||||
]);
|
<input type="text" class="form-select datetime" name="attribute_links[<?= $definition_id ?>]" id="attribute_links[<?= $definition_id ?>]" aria-describedby="attribute_links[<?= $definition_id ?>]-icon" value="<?= to_date($value) ?>" data-definition-id="<?= $definition_id ?>" readonly>
|
||||||
echo form_checkbox([
|
<button type="button" class="btn btn-outline-danger remove_attribute_btn"><i class="bi bi-trash"></i></button>
|
||||||
'name' => "attribute_links[$definition_id]",
|
|
||||||
'id' => "attribute_links[$definition_id]",
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $value == 1,
|
|
||||||
'class' => 'checkbox-inline',
|
|
||||||
'data-definition-id' => $definition_id
|
|
||||||
]);
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
?>
|
|
||||||
<span class="input-group-addon input-sm btn btn-default remove_attribute_btn">
|
|
||||||
<span class="glyphicon glyphicon-trash"></span>
|
|
||||||
</span>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
<?php
|
||||||
</div>
|
break;
|
||||||
|
|
||||||
|
case DROPDOWN:
|
||||||
|
$selected_value = $definition_value['selected_value'];
|
||||||
|
?>
|
||||||
|
<label for="attribute_links[<?= $definition_id ?>]" class="form-label"><?= esc($definition_value['definition_name']) ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="attribute_links[<?= $definition_id ?>]-icon"><i class="bi bi-menu-down"></i></span>
|
||||||
|
<input type="hidden" name="attribute_ids[<?= $definition_id ?>]" value="<?= strval($definition_value['attribute_id']) ?>">
|
||||||
|
<select class="form-select" name="attribute_links[<?= $definition_id ?>]" id="attribute_links[<?= $definition_id ?>]" data-definition-id="<?= $definition_id ?>">
|
||||||
|
<?php foreach ($definition_value['values'] as $key => $val): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $selected_value == $key ? 'selected' : '' ?>><?= $val ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
<button type="button" class="btn btn-outline-danger remove_attribute_btn"><i class="bi bi-trash"></i></button>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
break;
|
||||||
|
|
||||||
|
case TEXT:
|
||||||
|
$value = (empty($attribute_value) || empty($attribute_value->attribute_value)) ? $definition_value['selected_value'] : $attribute_value->attribute_value;
|
||||||
|
?>
|
||||||
|
<label for="attribute_links[<?= $definition_id ?>]" class="form-label"><?= esc($definition_value['definition_name']) ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="attribute_links[<?= $definition_id ?>]-icon"><i class="bi bi-type"></i></span>
|
||||||
|
<input type="hidden" name="attribute_ids[<?= $definition_id ?>]" value="<?= strval($definition_value['attribute_id']) ?>">
|
||||||
|
<input type="text" name="attribute_links[<?= $definition_id ?>]" id="attribute_links[<?= $definition_id ?>]" value="<?= esc($value) ?>" class="form-control valid_chars" data-definition-id="<?= $definition_id ?>">
|
||||||
|
<button type="button" class="btn btn-outline-danger remove_attribute_btn"><i class="bi bi-trash"></i></button>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
break;
|
||||||
|
|
||||||
|
case DECIMAL:
|
||||||
|
$value = (empty($attribute_value) || empty($attribute_value->attribute_decimal)) ? $definition_value['selected_value'] : $attribute_value->attribute_decimal;
|
||||||
|
?>
|
||||||
|
<label for="attribute_links[<?= $definition_id ?>]" class="form-label"><?= esc($definition_value['definition_name']) ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="attribute_links[<?= $definition_id ?>]-icon"><i class="bi bi-dot"></i></span>
|
||||||
|
<input type="hidden" name="attribute_ids[<?= $definition_id ?>]" value="<?= strval($definition_value['attribute_id']) ?>">
|
||||||
|
<input type="text" name="attribute_links[<?= $definition_id ?>]" id="attribute_links[<?= $definition_id ?>]" value="<?= to_decimals((float)$value) ?>" class="form-control valid_chars" data-definition-id="<?= $definition_id ?>">
|
||||||
|
<button type="button" class="btn btn-outline-danger remove_attribute_btn"><i class="bi bi-trash"></i></button>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
break;
|
||||||
|
|
||||||
|
case CHECKBOX:
|
||||||
|
$value = (empty($attribute_value) || empty($attribute_value->attribute_value)) ? $definition_value['selected_value'] : $attribute_value->attribute_value;
|
||||||
|
?>
|
||||||
|
<div class="d-flex justify-content-between">
|
||||||
|
<div class="form-check form-check-inline mb-3">
|
||||||
|
<input type="hidden" name="attribute_ids[<?= $definition_id ?>]" value="<?= strval($definition_value['attribute_id']) ?>">
|
||||||
|
<input type="hidden" name="attribute_links_h1[<?= $definition_id ?>]" id="attribute_links_h1<?= $definition_id ?>" value="0" data-definition-id="<?= $definition_id ?>">
|
||||||
|
<input type="checkbox" class="form-check-input" name="attribute_links[<?= $definition_id ?>]" id="attribute_links[<?= $definition_id ?>]" value="1" <?= $value == 1 ? 'checked' : '' ?> data-definition-id="<?= $definition_id ?>">
|
||||||
|
<label class="form-check-label" for="attribute_links[<?= $definition_id ?>]"><?= esc($definition_value['definition_name']) ?></label>
|
||||||
|
</div>
|
||||||
|
<button type="button" class="btn btn-outline-danger remove_attribute_btn"><i class="bi bi-trash"></i></button>
|
||||||
|
</div>
|
||||||
|
<?php
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
?>
|
||||||
|
</span>
|
||||||
|
|
||||||
<?php } ?>
|
<?php } ?>
|
||||||
|
|
||||||
@@ -106,7 +108,7 @@
|
|||||||
|
|
||||||
var enable_delete = function() {
|
var enable_delete = function() {
|
||||||
$('.remove_attribute_btn').click(function() {
|
$('.remove_attribute_btn').click(function() {
|
||||||
$(this).parents('.form-group').remove();
|
$(this).parents('.attribute_added').remove();
|
||||||
});
|
});
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -134,13 +136,13 @@
|
|||||||
$("[name*='attribute_links'").each(function() {
|
$("[name*='attribute_links'").each(function() {
|
||||||
var definition_id = $(this).data('definition-id');
|
var definition_id = $(this).data('definition-id');
|
||||||
var element = $(this);
|
var element = $(this);
|
||||||
|
|
||||||
// For checkboxes, use the visible checkbox, not the hidden input
|
// For checkboxes, use the visible checkbox, not the hidden input
|
||||||
if (element.attr('type') === 'hidden' && element.siblings('input[type="checkbox"]').length > 0) {
|
if (element.attr('type') === 'hidden' && element.siblings('input[type="checkbox"]').length > 0) {
|
||||||
// Skip hidden inputs that have a corresponding checkbox
|
// Skip hidden inputs that have a corresponding checkbox
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// For checkboxes, get the checked state
|
// For checkboxes, get the checked state
|
||||||
if (element.attr('type') === 'checkbox') {
|
if (element.attr('type') === 'checkbox') {
|
||||||
result[definition_id] = element.prop('checked') ? '1' : '0';
|
result[definition_id] = element.prop('checked') ? '1' : '0';
|
||||||
|
|||||||
@@ -8,6 +8,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Attributes';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
<?= view('partial/bootstrap_tables_locale') ?>
|
<?= view('partial/bootstrap_tables_locale') ?>
|
||||||
@@ -21,16 +26,16 @@
|
|||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div id="title_bar" class="btn-toolbar print_hide">
|
<div class="d-flex gap-2 justify-content-end d-print-none">
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . ".new") ?>">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . ".new") ?>">
|
||||||
<span class="glyphicon glyphicon-star"> </span><?= lang(ucfirst($controller_name) . ".new") ?>
|
<i class="bi bi-star me-2"></i><?= lang(ucfirst($controller_name) . ".new") ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left form-inline" role="toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm print_hide">
|
<button type="button" class="btn btn-secondary d-print-none" id="delete">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -11,31 +11,34 @@ $barcode_lib = new Barcode_lib();
|
|||||||
|
|
||||||
<!doctype html>
|
<!doctype html>
|
||||||
<html lang="<?= current_language_code() ?>">
|
<html lang="<?= current_language_code() ?>">
|
||||||
<head>
|
|
||||||
<meta charset="utf-8">
|
<head>
|
||||||
<title><?= lang('Items.generate_barcodes') ?></title>
|
<meta charset="utf-8">
|
||||||
<link rel="stylesheet" href="<?= base_url() ?>css/barcode_font.css">
|
<title><?= esc(lang('Items.generate_barcodes')) ?></title>
|
||||||
<style>
|
<link rel="stylesheet" href="<?= esc(base_url('css/barcode_font.css'), 'url') ?>">
|
||||||
.barcode svg {
|
<style>
|
||||||
height: <?= $barcode_config['barcode_height'] ?>px;
|
.barcode svg {
|
||||||
width: <?= $barcode_config['barcode_width'] ?>px;
|
height: <?= (int) $barcode_config['barcode_height'] ?>px;
|
||||||
}
|
width: <?= (int) $barcode_config['barcode_width'] ?>px;
|
||||||
</style>
|
}
|
||||||
</head>
|
</style>
|
||||||
<body class=<?= 'font_' . $barcode_lib->get_font_name($barcode_config['barcode_font']) ?> style="font-size: <?= $barcode_config['barcode_font_size'] ?>px;">
|
</head>
|
||||||
<table style="border-spacing: <?= $barcode_config['barcode_page_cellspacing'] ?>; width: <?= $barcode_config['barcode_page_width'] ?>%;">
|
|
||||||
<tr>
|
<body class="<?= esc('font_' . $barcode_lib->get_font_name($barcode_config['barcode_font']), 'attr') ?>" style="font-size: <?= (int) $barcode_config['barcode_font_size'] ?>px;">
|
||||||
<?php
|
<table style="border-spacing: <?= (int) $barcode_config['barcode_page_cellspacing'] ?>px; width: <?= (int) $barcode_config['barcode_page_width'] ?>%;">
|
||||||
$count = 0;
|
<tr>
|
||||||
foreach ($items as $item) {
|
<?php
|
||||||
if ($count % $barcode_config['barcode_num_in_row'] == 0 && $count != 0) {
|
$count = 0;
|
||||||
echo '</tr><tr>';
|
foreach ($items as $item) {
|
||||||
}
|
if ($count % $barcode_config['barcode_num_in_row'] == 0 && $count != 0) {
|
||||||
echo '<td>' . $barcode_lib->display_barcode($item, $barcode_config) . '</td>';
|
echo '</tr><tr>';
|
||||||
$count++;
|
|
||||||
}
|
}
|
||||||
?>
|
echo '<td>' . $barcode_lib->display_barcode($item, $barcode_config) . '</td>';
|
||||||
</tr>
|
$count++;
|
||||||
</table>
|
}
|
||||||
</body>
|
?>
|
||||||
|
</tr>
|
||||||
|
</table>
|
||||||
|
</body>
|
||||||
|
|
||||||
</html>
|
</html>
|
||||||
|
|||||||
@@ -7,244 +7,140 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open('cashups/save/' . $cash_ups_info->cashup_id, ['id' => 'cashups_edit_form']) // TODO: String Interpolation ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open('cashups/save/' . $cash_ups_info->cashup_id, ['id' => 'cashups_edit_form', 'class' => 'form-horizontal']) // TODO: String Interpolation ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="item_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="mb-3"><?= lang('Cashups.info') ?> <?= !empty($cash_ups_info->cashup_id) ? lang('Cashups.id') . " $cash_ups_info->cashup_id" : '' ?></div>
|
||||||
<?= form_label(lang('Cashups.info'), 'cash_ups_info', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<?= form_label(!empty($cash_ups_info->cashup_id) ? lang('Cashups.id') . ' ' . $cash_ups_info->cashup_id : '', 'cashup_id', ['class' => 'control-label col-xs-8', 'style' => 'text-align: left']) ?>
|
<label for="open_date" class="form-label"><?= lang('Cashups.open_date'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="open_date-icon"><i class="bi bi-calendar2-check"></i></span>
|
||||||
|
<input type="text" class="form-control datepicker" name="open_date" id="open_date" aria-describedby="open_date-icon" value="<?= to_datetime(strtotime($cash_ups_info->open_date)) ?>" required>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="open_employee" class="form-label"><?= lang('Cashups.open_employee'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="open_employee-icon"><i class="bi bi-person"></i></span>
|
||||||
|
<select class="form-select" name="open_employee_id" id="open_employee_id">
|
||||||
|
<?php foreach ($employees as $id => $name): ?>
|
||||||
|
<option value="<?= $id ?>" <?= $id == $cash_ups_info->open_employee_id ? 'selected' : '' ?>><?= esc($name) ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="open_amount_cash" class="form-label"><?= lang('Cashups.open_amount_cash'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="tax_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="open_amount_cash" id="open_amount_cash" aria-describedby="open_amount_cash-icon" value="<?= to_currency_no_money($cash_ups_info->open_amount_cash) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="tax_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="transfer_amount_cash" class="form-label"><?= lang('Cashups.transfer_amount_cash'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="transfer_amount_cash-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="transfer_amount_cash" id="transfer_amount_cash" aria-describedby="transfer_amount_cash-icon" value="<?= to_currency_no_money($cash_ups_info->transfer_amount_cash) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="transfer_amount_cash-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="close_date" class="form-label"><?= lang('Cashups.close_date'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="close_date-icon"><i class="bi bi-calendar2-x"></i></span>
|
||||||
|
<input type="text" class="form-control datepicker" name="close_date" id="close_date" aria-describedby="close_date-icon" value="<?= to_datetime(strtotime($cash_ups_info->close_date)) ?>" required>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="close_employee" class="form-label"><?= lang('Cashups.close_employee'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="close_employee-icon"><i class="bi bi-person"></i></span>
|
||||||
|
<select class="form-select" name="close_employee_id" id="close_employee_id">
|
||||||
|
<?php foreach ($employees as $id => $name): ?>
|
||||||
|
<option value="<?= $id ?>" <?= $id == $cash_ups_info->close_employee_id ? 'selected' : '' ?>><?= esc($name) ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="closed_amount_cash" class="form-label"><?= lang('Cashups.closed_amount_cash'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_cash-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="closed_amount_cash" id="closed_amount_cash" aria-describedby="closed_amount_cash-icon" value="<?= to_currency_no_money($cash_ups_info->closed_amount_cash) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_cash-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" name="note" id="note" value="0" <?= $cash_ups_info->note == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="note"><?= lang('Cashups.note') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="closed_amount_due" class="form-label"><?= lang('Cashups.closed_amount_due'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_due-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="closed_amount_due" id="closed_amount_due" aria-describedby="closed_amount_due-icon" value="<?= to_currency_no_money($cash_ups_info->closed_amount_due) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_due-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="closed_amount_card" class="form-label"><?= lang('Cashups.closed_amount_card'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_card-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="closed_amount_card" id="closed_amount_card" aria-describedby="closed_amount_card-icon" value="<?= to_currency_no_money($cash_ups_info->closed_amount_card) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_card-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="closed_amount_check" class="form-label"><?= lang('Cashups.closed_amount_check'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_check-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="closed_amount_check" id="closed_amount_check" aria-describedby="closed_amount_check-icon" value="<?= to_currency_no_money($cash_ups_info->closed_amount_check) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_check-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="closed_amount_total" class="form-label"><?= lang('Cashups.closed_amount_total'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_total-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input type="hidden" name="closed_amount_total" id="closed_amount_total" aria-describedby="closed_amount_total-icon" value="<?= to_currency_no_money($cash_ups_info->closed_amount_total) ?>">
|
||||||
|
<input type="text" class="form-control" value="<?= to_currency_no_money($cash_ups_info->closed_amount_total) ?>" readonly disabled>
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="closed_amount_total-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="description" class="form-label"><?= lang('Cashups.description'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-chat"></i></span>
|
||||||
|
<textarea class="form-control" name="description" id="description" rows="6"><?= $cash_ups_info->description ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<?php if (!empty($cash_ups_info->cashup_id)): ?>
|
||||||
|
<div class="form-check mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" name="deleted" id="deleted" value="1" <?= $cash_ups_info->deleted == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label text-danger" for="deleted"><?= lang('Cashups.is_deleted') ?></label>
|
||||||
</div>
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.open_date'), 'open_date', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-calendar"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'open_date',
|
|
||||||
'id' => 'open_date',
|
|
||||||
'class' => 'form-control input-sm datepicker',
|
|
||||||
'value' => to_datetime(strtotime($cash_ups_info->open_date))
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.open_employee'), 'open_employee', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_dropdown('open_employee_id', $employees, $cash_ups_info->open_employee_id, 'id="open_employee_id" class="form-control"') ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.open_amount_cash'), 'open_amount_cash', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'open_amount_cash',
|
|
||||||
'id' => 'open_amount_cash',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->open_amount_cash)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.transfer_amount_cash'), 'transfer_amount_cash', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'transfer_amount_cash',
|
|
||||||
'id' => 'transfer_amount_cash',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->transfer_amount_cash)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.close_date'), 'close_date', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-calendar"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'close_date',
|
|
||||||
'id' => 'close_date',
|
|
||||||
'class' => 'form-control input-sm datepicker',
|
|
||||||
'value' => to_datetime(strtotime($cash_ups_info->close_date))
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.close_employee'), 'close_employee', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_dropdown('close_employee_id', $employees, $cash_ups_info->close_employee_id, 'id="close_employee_id" class="form-control"') ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.closed_amount_cash'), 'closed_amount_cash', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'closed_amount_cash',
|
|
||||||
'id' => 'closed_amount_cash',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->closed_amount_cash)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.note'), 'note', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'note',
|
|
||||||
'id' => 'note',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $cash_ups_info->note == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.closed_amount_due'), 'closed_amount_due', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'closed_amount_due',
|
|
||||||
'id' => 'closed_amount_due',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->closed_amount_due)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.closed_amount_card'), 'closed_amount_card', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'closed_amount_card',
|
|
||||||
'id' => 'closed_amount_card',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->closed_amount_card)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.closed_amount_check'), 'closed_amount_check', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'closed_amount_check',
|
|
||||||
'id' => 'closed_amount_check',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->closed_amount_check)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.closed_amount_total'), 'closed_amount_total', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'closed_amount_total',
|
|
||||||
'id' => 'closed_amount_total',
|
|
||||||
'readonly' => 'true',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($cash_ups_info->closed_amount_total)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.description'), 'description', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'description',
|
|
||||||
'id' => 'description',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $cash_ups_info->description
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php if (!empty($cash_ups_info->cashup_id)) { ?>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Cashups.is_deleted') . ':', 'deleted', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-5">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'deleted',
|
|
||||||
'id' => 'deleted',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $cash_ups_info->deleted == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
@@ -12,6 +12,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Cashups';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
// Load the preset datarange picker
|
// Load the preset datarange picker
|
||||||
@@ -46,29 +51,36 @@
|
|||||||
|
|
||||||
<?= view('partial/print_receipt', ['print_after_sale' => false, 'selected_printer' => 'takings_printer']) ?>
|
<?= view('partial/print_receipt', ['print_after_sale' => false, 'selected_printer' => 'takings_printer']) ?>
|
||||||
|
|
||||||
<div id="title_bar" class="print_hide btn-toolbar">
|
<div id="title_bar" class="d-flex gap-2 justify-content-end d-print-none">
|
||||||
<button onclick="printdoc()" class="btn btn-info btn-sm pull-right">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= "$controller_name/view" ?>" title="<?= lang(ucfirst($controller_name) . ".new") ?>">
|
||||||
<span class="glyphicon glyphicon-print"> </span><?= lang('Common.print') ?>
|
<i class="bi bi-journal-check me-2"></i><?= lang(esc(ucfirst($controller_name)) . '.new') // TODO: String Interpolation ?>
|
||||||
</button>
|
</button>
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= "$controller_name/view" ?>" title="<?= lang(ucfirst($controller_name) . ".new") ?>">
|
<button type="button" class="btn btn-primary" onclick="window.print()" title="<?= lang('Common.print') ?>">
|
||||||
<span class="glyphicon glyphicon-tags"> </span><?= lang(esc(ucfirst($controller_name)) . '.new') // TODO: String Interpolation ?>
|
<i class="bi bi-printer me-2"></i><?= lang('Common.print') ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left form-inline" role="toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm print_hide">
|
<button type="button" id="delete" class="btn btn-secondary d-print-none">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
<?= form_input(['name' => 'daterangepicker', 'class' => 'form-control input-sm', 'id' => 'daterangepicker']) ?>
|
|
||||||
<?= form_multiselect('filters[]', $filters, $selected_filters ?? [], [
|
<div class="input-group w-auto">
|
||||||
'id' => 'filters',
|
<span class="input-group-text" id="daterangepicker-icon"><i class="bi bi-calendar2-range"></i></span>
|
||||||
'data-none-selected-text' => lang('Common.none_selected_text'),
|
<input type="text" class="form-select" name="daterangepicker" id="daterangepicker" aria-describedby="daterangepicker-icon">
|
||||||
'class' => 'selectpicker show-menu-arrow',
|
</div>
|
||||||
'data-selected-text-format' => 'count > 1',
|
|
||||||
'data-style' => 'btn-default btn-sm',
|
<div class="input-group w-auto">
|
||||||
'data-width' => 'fit'
|
<span class="input-group-text" id="filters-icon"><i class="bi bi-funnel"></i></span>
|
||||||
]) ?>
|
<select class="form-select" name="filters[]" id="filters" aria-describedby="filters-icon" multiple>
|
||||||
|
<?php foreach ($filters as $key => $label): ?>
|
||||||
|
<option value="<?= $key ?>" <?= in_array($key, $selected_filters ?? []) ? 'selected' : '' ?>>
|
||||||
|
<?= esc($label) ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -77,3 +89,15 @@
|
|||||||
</div>
|
</div>
|
||||||
|
|
||||||
<?= view('partial/footer') ?>
|
<?= view('partial/footer') ?>
|
||||||
|
|
||||||
|
<script type="text/javascript">
|
||||||
|
new TomSelect('#filters', {
|
||||||
|
plugins: ['checkbox_options', 'remove_button'],
|
||||||
|
placeholder: '<?= lang('Common.none_selected_text') ?>',
|
||||||
|
hidePlaceholder: true,
|
||||||
|
closeAfterSelect: false,
|
||||||
|
onChange: function() {
|
||||||
|
$('#table').bootstrapTable('refresh');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|||||||
124
app/Views/configs/appearance_config.php
Normal file
124
app/Views/configs/appearance_config.php
Normal file
@@ -0,0 +1,124 @@
|
|||||||
|
<?php
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
*/
|
||||||
|
|
||||||
|
$beta = '<sup><span class="badge bg-secondary">BETA</span></sup>';
|
||||||
|
?>
|
||||||
|
|
||||||
|
<?= form_open('config/saveAppearance/', ['id' => 'appearance_config_form']) ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Appearance';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
|
<ul id="error_message_box" class="appearance_error_message_box alert alert-warning d-none"></ul>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="theme-change" class="form-label"><?= lang('Config.theme'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-binoculars"></i></span>
|
||||||
|
<select class="form-select" name="theme" id="theme-change">
|
||||||
|
<?php foreach ($themes as $value => $display): ?>
|
||||||
|
<option value="<?= $value ?>" <?= $config['theme'] == $value ? 'selected' : '' ?>><?= $display ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="login_form" class="form-label"><?= lang('Config.login_form'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-view-stacked"></i></span>
|
||||||
|
<select class="form-select" name="login_form" id="login_form">
|
||||||
|
<option value="floating_labels" <?= $config['login_form'] == 'floating_labels' ? 'selected' : '' ?>><?= lang('Config.floating_labels') ?></option>
|
||||||
|
<option value="input_groups" <?= $config['login_form'] == 'input_groups' ? 'selected' : '' ?>><?= lang('Config.input_groups') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="color_mode" class="form-label">Color Mode <?= $beta; ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="color-mode-icon"><i class="bi bi-palette"></i></span>
|
||||||
|
<select class="form-select" id="color_mode" name="color_mode" aria-describedby="color-mode-icon">
|
||||||
|
<option value="light" <?= $config['color_mode'] == 'light' ? 'selected' : '' ?>>Light</option>
|
||||||
|
<option value="dark" <?= $config['color_mode'] == 'dark' ? 'selected' : '' ?>>Dark</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="notify_position" class="form-label"><?= lang('Config.notify_alignment'); ?></label>
|
||||||
|
<div class="row" id="notify_position">
|
||||||
|
<div class="col-6 mb-3">
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-down-up"></i></span>
|
||||||
|
<select class="form-select" name="notify_vertical_position">
|
||||||
|
<option value="top" <?= $config['notify_vertical_position'] == 'top' ? 'selected' : '' ?>><?= lang('Config.top') ?></option>
|
||||||
|
<option value="bottom" <?= $config['notify_vertical_position'] == 'bottom' ? 'selected' : '' ?>><?= lang('Config.bottom') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="col-6 mb-3">
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-left-right"></i></span>
|
||||||
|
<select class="form-select" name="notify_horizontal_position">
|
||||||
|
<option value="left" <?= $config['notify_horizontal_position'] == 'left' ? 'selected' : '' ?>><?= lang('Config.left') ?></option>
|
||||||
|
<option value="center" <?= $config['notify_horizontal_position'] == 'center' ? 'selected' : '' ?>><?= lang('Config.center') ?></option>
|
||||||
|
<option value="right" <?= $config['notify_horizontal_position'] == 'right' ? 'selected' : '' ?>><?= lang('Config.right') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="config_menu_position" class="form-label">Configuration Menu Position</label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="config-menu-position-icon"><i class="bi bi-distribute-horizontal"></i></span>
|
||||||
|
<select class="form-select" id="config_menu_position" name="config_menu_position" aria-describedby="config-menu-position-icon">
|
||||||
|
<option value="start" <?= $config['config_menu_position'] == 'start' ? 'selected' : '' ?>>Start</option>
|
||||||
|
<option value="end" <?= $config['config_menu_position'] == 'end' ? 'selected' : '' ?>>End</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="responsive_design" name="responsive_design" value="responsive_design" <?= $config['responsive_design'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="responsive_design">Responsive Design <?= $beta; ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_appearance"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<?= form_close() ?>
|
||||||
|
|
||||||
|
<script type="application/javascript">
|
||||||
|
// Validation and submit handling
|
||||||
|
$(document).ready(function() {
|
||||||
|
$('#appearance_config_form').validate($.extend(form_support.handler, {
|
||||||
|
submitHandler: function(form) {
|
||||||
|
$(form).ajaxSubmit({
|
||||||
|
success: function(response) {
|
||||||
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
|
message: response.message + ' <em>Click to refresh.</em>',
|
||||||
|
url: 'javascript:window.location.reload();',
|
||||||
|
target: '_self'
|
||||||
|
}, {
|
||||||
|
type: response.success ? 'success' : 'danger'
|
||||||
|
})
|
||||||
|
},
|
||||||
|
dataType: 'json'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
errorLabelContainer: '.appearance_error_message_box'
|
||||||
|
}));
|
||||||
|
});
|
||||||
|
</script>
|
||||||
@@ -6,251 +6,194 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveBarcode/', ['id' => 'barcode_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveBarcode/', ['id' => 'barcode_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="barcode_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.barcode_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="barcode_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.barcode_type'), 'barcode_type', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
<div class="row">
|
||||||
<?= form_dropdown(
|
<div class="col-12 col-lg-6">
|
||||||
'barcode_type',
|
<label for="barcode_type" class="form-label"><?= lang('Config.barcode_type'); ?></label>
|
||||||
$support_barcode,
|
<div class="input-group mb-3">
|
||||||
$config['barcode_type'],
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
'class="form-control input-sm"'
|
<select class="form-select" name="barcode_type" id="barcode_type">
|
||||||
) ?>
|
<?php foreach ($support_barcode as $key => $value): ?>
|
||||||
</div>
|
<option value="<?= $key ?>" <?= $config['barcode_type'] == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-6 col-lg-3">
|
||||||
<?= form_label(lang('Config.barcode_width'), 'barcode_width', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="barcode_width" class="form-label"><?= lang('Config.barcode_width'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-arrows"></i></span>
|
||||||
'step' => '5',
|
<input type="number" class="form-control" step="5" max="350" min="60" name="barcode_width" id="barcode_width" value="<?= $config['barcode_width'] ?>" required>
|
||||||
'max' => '350',
|
<span class="input-group-text">px</span>
|
||||||
'min' => '60',
|
|
||||||
'type' => 'number',
|
|
||||||
'name' => 'barcode_width',
|
|
||||||
'id' => 'barcode_width',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_width']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-6 col-lg-3">
|
||||||
<?= form_label(lang('Config.barcode_height'), 'barcode_height', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="barcode_height" class="form-label"><?= lang('Config.barcode_height'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-arrows-vertical"></i></span>
|
||||||
'type' => 'number',
|
<input type="number" class="form-control" min="10" max="120" name="barcode_height" id="barcode_height" value="<?= $config['barcode_height'] ?>" required>
|
||||||
'min' => 10,
|
<span class="input-group-text">px</span>
|
||||||
'max' => 120,
|
|
||||||
'name' => 'barcode_height',
|
|
||||||
'id' => 'barcode_height',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_height']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_font'), 'barcode_font', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'barcode_font',
|
|
||||||
$barcode_fonts,
|
|
||||||
$config['barcode_font'],
|
|
||||||
'class="form-control input-sm" required'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => '1',
|
|
||||||
'max' => '30',
|
|
||||||
'name' => 'barcode_font_size',
|
|
||||||
'id' => 'barcode_font_size',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_font_size']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.allow_duplicate_barcodes'), 'allow_duplicate_barcodes', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'allow_duplicate_barcodes',
|
|
||||||
'id' => 'allow_duplicate_barcodes',
|
|
||||||
'value' => 'allow_duplicate_barcodes',
|
|
||||||
'checked' => $config['allow_duplicate_barcodes'] == 1
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
<label class="control-label">
|
|
||||||
<span class="glyphicon glyphicon-warning-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.barcode_tooltip') ?>"></span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_content'), 'barcode_content', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'barcode_content',
|
|
||||||
'value' => 'id',
|
|
||||||
'checked' => $config['barcode_content'] == 'id'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.barcode_id') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'barcode_content',
|
|
||||||
'value' => 'number',
|
|
||||||
'checked' => $config['barcode_content'] == 'number'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.barcode_number') ?>
|
|
||||||
</label>
|
|
||||||
|
|
||||||
|
|
||||||
<label class="checkbox-inline">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'barcode_generate_if_empty',
|
|
||||||
'value' => 'barcode_generate_if_empty',
|
|
||||||
'checked' => $config['barcode_generate_if_empty'] == 1
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.barcode_generate_if_empty') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_formats'), 'barcode_formats', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?php
|
|
||||||
$barcode_formats = json_decode(config('OSPOS')->settings['barcode_formats']);
|
|
||||||
echo form_dropdown([
|
|
||||||
'name' => 'barcode_formats[]',
|
|
||||||
'id' => 'barcode_formats',
|
|
||||||
'options' => !empty($barcode_formats) ? array_combine($barcode_formats, $barcode_formats) : [],
|
|
||||||
'multiple' => 'multiple',
|
|
||||||
'data-role' => 'tagsinput'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_layout'), 'barcode_layout', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-10">
|
|
||||||
<div class="form-group form-group-sm row">
|
|
||||||
<label class="control-label col-sm-1"><?= lang('Config.barcode_first_row') . ' ' ?></label>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'barcode_first_row',
|
|
||||||
[
|
|
||||||
'not_show' => lang('Config.none'),
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'category' => lang('Items.category'),
|
|
||||||
'cost_price' => lang('Items.cost_price'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'company_name' => lang('Suppliers.company_name')
|
|
||||||
],
|
|
||||||
$config['barcode_first_row'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
); ?>
|
|
||||||
</div>
|
|
||||||
<label class="control-label col-sm-1"><?= lang('Config.barcode_second_row') . ' ' ?></label>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'barcode_second_row',
|
|
||||||
[
|
|
||||||
'not_show' => lang('Config.none'),
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'category' => lang('Items.category'),
|
|
||||||
'cost_price' => lang('Items.cost_price'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'item_code' => lang('Items.item_number'),
|
|
||||||
'company_name' => lang('Suppliers.company_name')
|
|
||||||
],
|
|
||||||
$config['barcode_second_row'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
<label class="control-label col-sm-1"><?= lang('Config.barcode_third_row') . ' ' ?></label>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'barcode_third_row',
|
|
||||||
[
|
|
||||||
'not_show' => lang('Config.none'),
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'category' => lang('Items.category'),
|
|
||||||
'cost_price' => lang('Items.cost_price'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'item_code' => lang('Items.item_number'),
|
|
||||||
'company_name' => lang('Suppliers.company_name')
|
|
||||||
],
|
|
||||||
$config['barcode_third_row'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_number_in_row'), 'barcode_num_in_row', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'barcode_num_in_row',
|
|
||||||
'id' => 'barcode_num_in_row',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_num_in_row']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_page_width'), 'barcode_page_width', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'barcode_page_width',
|
|
||||||
'id' => 'barcode_page_width',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_page_width']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">%</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.barcode_page_cellspacing'), 'barcode_page_cellspacing', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'barcode_page_cellspacing',
|
|
||||||
'id' => 'barcode_page_cellspacing',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['barcode_page_cellspacing']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_barcode',
|
|
||||||
'id' => 'submit_barcode',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="barcode_font" class="form-label"><?= lang('Config.barcode_font'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-fonts"></i></span>
|
||||||
|
<select class="form-select" id="barcode_font" name="barcode_font" required>
|
||||||
|
<?php foreach ($barcode_fonts as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $config['barcode_font'] == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="barcode_font_size" class="form-label">Font Size<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrows-angle-expand"></i></span>
|
||||||
|
<input type="number" class="form-control" min="1" max="30" name="barcode_font_size" id="barcode_font_size" value="<?= $config['barcode_font_size'] ?>" required>
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="allow_duplicate_barcodes" name="allow_duplicate_barcodes" value="allow_duplicate_barcodes" <?= $config['allow_duplicate_barcodes'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="allow_duplicate_barcodes"><?= lang('Config.allow_duplicate_barcodes'); ?></label>
|
||||||
|
<div class="form-text"><i class="bi bi-info-square pe-1"></i><?= lang('Config.barcode_tooltip') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="barcode_content" class="form-label"><?= lang('Config.barcode_content'); ?></label>
|
||||||
|
<div class="row mb-3">
|
||||||
|
<div class="col-12">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="barcode_content" id="barcode_content_id" value="id" <?= $config['barcode_content'] == 'id' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="barcode_content_id"><?= lang('Config.barcode_id') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="barcode_content" id="barcode_content_number" value="number" <?= $config['barcode_content'] == 'number' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="barcode_content_number"><?= lang('Config.barcode_number') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline form-switch">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="barcode_generate_if_empty" name="barcode_generate_if_empty" value="barcode_generate_if_empty" <?= $config['barcode_generate_if_empty'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="barcode_generate_if_empty"><?= lang('Config.barcode_generate_if_empty'); ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="barcode_formats" class="form-label"><?= lang('Config.barcode_formats'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-code-square"></i></span>
|
||||||
|
<!-- <?php
|
||||||
|
$barcode_formats = json_decode(config('OSPOS')->settings['barcode_formats']);
|
||||||
|
$options = !empty($barcode_formats) ? array_combine($barcode_formats, $barcode_formats) : [];
|
||||||
|
?>
|
||||||
|
<select class="form-select" id="barcode_formats" name="barcode_formats[]" data-role="tagsinput" multiple>
|
||||||
|
<?php foreach ($options as $value): ?>
|
||||||
|
<option value="<?= $value ?>" <?= in_array($value, $barcode_formats) ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select> -->
|
||||||
|
<input type="text" class="form-control" disabled>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<label for="barcode_layout" class="form-label"><?= lang('Config.barcode_layout'); ?></label>
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-1-square"></i></span>
|
||||||
|
<select name="barcode_first_row" class="form-select">
|
||||||
|
<option value="not_show" <?= $config['barcode_first_row'] == 'not_show' ? 'selected' : '' ?>><?= lang('Config.none') ?></option>
|
||||||
|
<option value="name" <?= $config['barcode_first_row'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="category" <?= $config['barcode_first_row'] == 'category' ? 'selected' : '' ?>><?= lang('Items.category') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['barcode_first_row'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['barcode_first_row'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="company_name" <?= $config['barcode_first_row'] == 'company_name' ? 'selected' : '' ?>><?= lang('Suppliers.company_name') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-2-square"></i></span>
|
||||||
|
<select name="barcode_second_row" class="form-select">
|
||||||
|
<option value="not_show" <?= $config['barcode_second_row'] == 'not_show' ? 'selected' : '' ?>><?= lang('Config.none') ?></option>
|
||||||
|
<option value="name" <?= $config['barcode_second_row'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="category" <?= $config['barcode_second_row'] == 'category' ? 'selected' : '' ?>><?= lang('Items.category') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['barcode_second_row'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['barcode_second_row'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="item_code" <?= $config['barcode_second_row'] == 'item_code' ? 'selected' : '' ?>><?= lang('Items.item_number') ?></option>
|
||||||
|
<option value="company_name" <?= $config['barcode_second_row'] == 'company_name' ? 'selected' : '' ?>><?= lang('Suppliers.company_name') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-3-square"></i></span>
|
||||||
|
<select name="barcode_third_row" class="form-select">
|
||||||
|
<option value="not_show" <?= $config['barcode_third_row'] == 'not_show' ? 'selected' : '' ?>><?= lang('Config.none') ?></option>
|
||||||
|
<option value="name" <?= $config['barcode_third_row'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="category" <?= $config['barcode_third_row'] == 'category' ? 'selected' : '' ?>><?= lang('Items.category') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['barcode_third_row'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['barcode_third_row'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="item_code" <?= $config['barcode_third_row'] == 'item_code' ? 'selected' : '' ?>><?= lang('Items.item_number') ?></option>
|
||||||
|
<option value="company_name" <?= $config['barcode_third_row'] == 'company_name' ? 'selected' : '' ?>><?= lang('Suppliers.company_name') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="barcode_num_in_row" class="form-label"><?= lang('Config.barcode_number_in_row'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="number" name="barcode_num_in_row" id="barcode_num_in_row" class="form-control" value="<?= $config['barcode_num_in_row'] ?>" required>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="barcode_page_width" class="form-label"><?= lang('Config.barcode_page_width'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrows"></i></span>
|
||||||
|
<input type="number" min="0" max="100" name="barcode_page_width" id="barcode_page_width" class="form-control" value="<?= $config['barcode_page_width'] ?>" required>
|
||||||
|
<span class="input-group-text"><i class="bi bi-percent"></i></span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="barcode_page_cellspacing" class="form-label"><?= lang('Config.barcode_page_cellspacing'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-distribute-horizontal"></i></span>
|
||||||
|
<input type="number" name="barcode_page_cellspacing" id="barcode_page_cellspacing" class="form-control" value="<?= $config['barcode_page_cellspacing'] ?>" required>
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_barcode"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -258,7 +201,7 @@
|
|||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
$('#barcode_config_form').validate($.extend(form_support.handler, {
|
$('#barcode_config_form').validate($.extend(form_support.handler, {
|
||||||
|
|
||||||
errorLabelContainer: "#barcode_error_message_box",
|
errorLabelContainer: ".barcode_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
barcode_width: {
|
barcode_width: {
|
||||||
|
|||||||
5
app/Views/configs/config_header.php
Normal file
5
app/Views/configs/config_header.php
Normal file
@@ -0,0 +1,5 @@
|
|||||||
|
<div class="d-flex">
|
||||||
|
<h4 class="flex-grow-1 fw-bold"><?= $config_title; ?></h4>
|
||||||
|
<h5 class="link-secondary d-print-none" data-bs-toggle="tooltip" data-bs-placement="bottom" title="Learn more in our docs"><i class="bi bi-journal-arrow-up"></i></h5>
|
||||||
|
</div>
|
||||||
|
<hr class="mt-0 d-print-none">
|
||||||
@@ -4,136 +4,85 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveEmail/', ['id' => 'email_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveEmail/', ['id' => 'email_config_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="email_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.email_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="email_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.email_protocol'), 'protocol', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
<div class="row">
|
||||||
<?= form_dropdown(
|
<div class="col-12 col-lg-6">
|
||||||
'protocol',
|
<label for="protocol" class="form-label"><?= lang('Config.email_protocol'); ?></label>
|
||||||
[
|
<div class="input-group mb-3">
|
||||||
'mail' => 'mail',
|
<span class="input-group-text"><i class="bi bi-mailbox"></i></span>
|
||||||
'sendmail' => 'sendmail',
|
<?= form_dropdown('protocol', array('mail' => 'Mail', 'sendmail' => 'Sendmail', 'smtp' => 'SMTP'), $config['protocol'], array('class' => 'form-select', 'id' => 'protocol')); ?>
|
||||||
'smtp' => 'smtp'
|
|
||||||
],
|
|
||||||
$config['protocol'],
|
|
||||||
'class="form-control input-sm" id="protocol"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_mailpath'), 'mailpath', ['class' => 'control-label col-xs-2']) ?>
|
<label for="mailpath" class="form-label"><?= lang('Config.email_mailpath'); ?></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
'name' => 'mailpath',
|
<input type="text" name="mailpath" class="form-control" id="mailpath" value="<?= $config['mailpath']; ?>">
|
||||||
'id' => 'mailpath',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['mailpath']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_host'), 'smtp_host', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_host" class="form-label"><?= lang('Config.email_smtp_host'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-database"></i></span>
|
||||||
'name' => 'smtp_host',
|
<input type="text" name="smtp_host" class="form-control" id="smtp_host" value="<?= $config['smtp_host']; ?>">
|
||||||
'id' => 'smtp_host',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['smtp_host']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_port'), 'smtp_port', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_port" class="form-label"><?= lang('Config.email_smtp_port'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-door-open"></i></span>
|
||||||
'name' => 'smtp_port',
|
<input type="number" name="smtp_port" class="form-control" id="smtp_port" value="<?= $config['smtp_port']; ?>">
|
||||||
'id' => 'smtp_port',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['smtp_port']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_crypto'), 'smtp_crypto', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_crypto" class="form-label"><?= lang('Config.email_smtp_crypto'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_dropdown(
|
<span class="input-group-text"><i class="bi bi-shield-lock"></i></span>
|
||||||
'smtp_crypto',
|
<?= form_dropdown('smtp_crypto', array('' => 'None', 'tls' => 'TLS', 'ssl' => 'SSL'), $config['smtp_crypto'], array('class' => 'form-select', 'id' => 'smtp_crypto')); ?>
|
||||||
[
|
|
||||||
'' => 'None',
|
|
||||||
'tls' => 'TLS',
|
|
||||||
'ssl' => 'SSL'
|
|
||||||
],
|
|
||||||
$config['smtp_crypto'],
|
|
||||||
'class="form-control input-sm" id="smtp_crypto"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_timeout'), 'smtp_timeout', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_timeout" class="form-label"><?= lang('Config.email_smtp_timeout'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text"><i class="bi bi-stopwatch"></i></span>
|
||||||
'name' => 'smtp_timeout',
|
<input type="number" name="smtp_timeout" class="form-control" id="smtp_timeout" value="<?= $config['smtp_timeout']; ?>">
|
||||||
'id' => 'smtp_timeout',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['smtp_timeout']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_user'), 'smtp_user', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_user" class="form-label"><?= lang('Config.email_smtp_user'); ?></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group mb-3">
|
||||||
<div class="input-group">
|
<span class="input-group-text"><i class="bi bi-person"></i></span>
|
||||||
<span class="input-group-addon input-sm">
|
<input type="text" name="smtp_user" class="form-control" id="smtp_user" value="<?= $config['smtp_user']; ?>">
|
||||||
<span class="glyphicon glyphicon-user"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'smtp_user',
|
|
||||||
'id' => 'smtp_user',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['smtp_user']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<?= form_label(lang('Config.email_smtp_pass'), 'smtp_pass', ['class' => 'control-label col-xs-2']) ?>
|
<label for="smtp_pass" class="form-label"><?= lang('Config.email_smtp_pass'); ?></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group mb-3">
|
||||||
<div class="input-group">
|
<span class="input-group-text"><i class="bi bi-lock"></i></span>
|
||||||
<span class="input-group-addon input-sm">
|
<input type="password" name="smtp_pass" class="form-control" id="smtp_pass" value="<?= $config['smtp_pass']; ?>">
|
||||||
<span class="glyphicon glyphicon-asterisk"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_password([
|
|
||||||
'name' => 'smtp_pass',
|
|
||||||
'id' => 'smtp_pass',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['smtp_pass']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_email',
|
|
||||||
'id' => 'submit_email',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_email"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -162,6 +111,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -173,7 +123,7 @@
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: '#email_error_message_box'
|
errorLabelContainer: '.email_error_message_box'
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -9,459 +9,209 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveGeneral/', ['id' => 'general_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveGeneral/', ['id' => 'general_config_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="general_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.general_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="general_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.theme'), 'theme', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-10">
|
<div class="row">
|
||||||
<div class="form-group form-group-sm row">
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
<div class="col-sm-3">
|
<label for="default_sales_discount" class="form-label"><?= lang('Config.default_sales_discount') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<?= form_dropdown(
|
<div class="input-group mb-3">
|
||||||
'theme',
|
<span class="input-group-text"><i class="bi bi-cart-dash"></i></span>
|
||||||
$themes,
|
<input class="form-control" type="number" min="0" max="100" name="default_sales_discount" id="default_sales_discount" value="<?= $config['default_sales_discount'] ?>" required>
|
||||||
$config['theme'],
|
<input type="radio" class="btn-check" name="default_sales_discount_type" id="dsd_type_1" value="1" <?= $config['default_sales_discount_type'] == 1 ? 'checked' : '' ?>>
|
||||||
'class="form-control input-sm" id="theme-change"'
|
<label class="btn btn-outline-primary fw-semibold" for="dsd_type_1"><?= $config['currency_symbol'] ?></label>
|
||||||
) ?>
|
<input type="radio" class="btn-check" name="default_sales_discount_type" id="dsd_type_0" value="0" <?= $config['default_sales_discount_type'] == 0 ? 'checked' : '' ?>>
|
||||||
</div>
|
<label class="btn btn-outline-primary fw-semibold" for="dsd_type_0">%</label>
|
||||||
<div class="col-sm-7">
|
|
||||||
<a href="<?= 'https://bootswatch.com/3/' . ('bootstrap' == ($config['theme']) ? 'default' : esc($config['theme'])) ?>" target="_blank" rel=”noopener”>
|
|
||||||
<span><?= lang('Config.theme_preview') . ' ' . ucfirst(esc($config['theme'])) . ' ' ?></span>
|
|
||||||
<span class="glyphicon glyphicon-new-window"></span>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
<?= form_label(lang('Config.login_form'), 'login_form', ['class' => 'control-label col-xs-2']) ?>
|
<label for="default_receivings_discount" class="form-label"><?= lang('Config.default_receivings_discount') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<?= form_dropdown(
|
<span class="input-group-text"><i class="bi bi-bag-dash"></i></span>
|
||||||
'login_form',
|
<input class="form-control" type="number" min="0" max="100" name="default_receivings_discount" id="default_receivings_discount" value="<?= $config['default_receivings_discount'] ?>" required>
|
||||||
[
|
<input type="radio" class="btn-check" name="default_receivings_discount_type" id="drd_type_1" value="1" <?= $config['default_receivings_discount_type'] == 1 ? 'checked' : '' ?>>
|
||||||
'floating_labels' => lang('Config.floating_labels'),
|
<label class="btn btn-outline-primary fw-semibold" for="drd_type_1"><?= $config['currency_symbol'] ?></label>
|
||||||
'input_groups' => lang('Config.input_groups')
|
<input type="radio" class="btn-check" name="default_receivings_discount_type" id="drd_type_0" value="0" <?= $config['default_receivings_discount_type'] == 0 ? 'checked' : '' ?>>
|
||||||
],
|
<label class="btn btn-outline-primary fw-semibold" for="drd_type_0">%</label>
|
||||||
$config['login_form'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_sales_discount'), 'default_sales_discount', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_sales_discount',
|
|
||||||
'id' => 'default_sales_discount',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 0,
|
|
||||||
'max' => 100,
|
|
||||||
'value' => $config['default_sales_discount']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-btn">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'id' => 'default_sales_discount_type',
|
|
||||||
'name' => 'default_sales_discount_type',
|
|
||||||
'value' => 1,
|
|
||||||
'data-toggle' => 'toggle',
|
|
||||||
'data-size' => 'normal',
|
|
||||||
'data-onstyle' => 'success',
|
|
||||||
'data-on' => '<b>' . $config['currency_symbol'] . '</b>',
|
|
||||||
'data-off' => '<b>%</b>',
|
|
||||||
'checked' => $config['default_sales_discount_type'] == 1
|
|
||||||
]) ?>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_receivings_discount'), 'default_receivings_discount', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_receivings_discount',
|
|
||||||
'id' => 'default_receivings_discount',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 0,
|
|
||||||
'max' => 100,
|
|
||||||
'value' => $config['default_receivings_discount']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-btn">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'id' => 'default_receivings_discount_type',
|
|
||||||
'name' => 'default_receivings_discount_type',
|
|
||||||
'value' => 1,
|
|
||||||
'data-toggle' => 'toggle',
|
|
||||||
'data-size' => 'normal',
|
|
||||||
'data-onstyle' => 'success',
|
|
||||||
'data-on' => '<b>' . $config['currency_symbol'] . '</b>',
|
|
||||||
'data-off' => '<b>%</b>',
|
|
||||||
'checked' => $config['default_receivings_discount_type'] == 1
|
|
||||||
]) ?>
|
|
||||||
</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.enforce_privacy'), 'enforce_privacy', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'enforce_privacy',
|
|
||||||
'id' => 'enforce_privacy',
|
|
||||||
'value' => 'enforce_privacy',
|
|
||||||
'checked' => $config['enforce_privacy'] == 1
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
<label class="control-label">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.enforce_privacy_tooltip') ?>"></span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receiving_calculate_average_price'), 'receiving_calculate_average_price', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receiving_calculate_average_price',
|
|
||||||
'id' => 'receiving_calculate_average_price',
|
|
||||||
'value' => 'receiving_calculate_average_price',
|
|
||||||
'checked' => $config['receiving_calculate_average_price'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.lines_per_page'), 'lines_per_page', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'lines_per_page',
|
|
||||||
'id' => 'lines_per_page',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 10,
|
|
||||||
'max' => 1000,
|
|
||||||
'value' => $config['lines_per_page']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.notify_alignment'), 'notify_horizontal_position', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-10">
|
|
||||||
<div class="form-group form-group-sm row">
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'notify_vertical_position',
|
|
||||||
[
|
|
||||||
'top' => lang('Config.top'),
|
|
||||||
'bottom' => lang('Config.bottom')
|
|
||||||
],
|
|
||||||
$config['notify_vertical_position'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'notify_horizontal_position',
|
|
||||||
[
|
|
||||||
'left' => lang('Config.left'),
|
|
||||||
'center' => lang('Config.center'),
|
|
||||||
'right' => lang('Config.right')
|
|
||||||
],
|
|
||||||
$config['notify_horizontal_position'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.image_restrictions'), 'image_restrictions', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-10">
|
|
||||||
<div class="form-group form-group-sm row">
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-resize-horizontal"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'image_max_width',
|
|
||||||
'id' => 'image_max_width',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 128,
|
|
||||||
'max' => 3840,
|
|
||||||
'value' => $config['image_max_width'],
|
|
||||||
'data-toggle' => 'tooltip',
|
|
||||||
'data-placement' => 'top',
|
|
||||||
'title' => lang('Config.image_max_width_tooltip')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-resize-vertical"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'image_max_height',
|
|
||||||
'id' => 'image_max_height',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 128,
|
|
||||||
'max' => 3840,
|
|
||||||
'value' => $config['image_max_height'],
|
|
||||||
'data-toggle' => 'tooltip',
|
|
||||||
'data-placement' => 'top',
|
|
||||||
'title' => lang('Config.image_max_height_tooltip')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-hdd"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'image_max_size',
|
|
||||||
'id' => 'image_max_size',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => 128,
|
|
||||||
'max' => 2048,
|
|
||||||
'value' => $config['image_max_size'],
|
|
||||||
'data-toggle' => 'tooltip',
|
|
||||||
'data-placement' => 'top',
|
|
||||||
'title' => lang('Config.image_max_size_tooltip')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-4">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><?= lang('Config.image_allowed_file_types') ?></span>
|
|
||||||
<?= form_multiselect([
|
|
||||||
'name' => 'image_allowed_types[]',
|
|
||||||
'options' => $image_allowed_types,
|
|
||||||
'selected' => $selected_image_allowed_types,
|
|
||||||
'id' => 'image_allowed_types',
|
|
||||||
'class' => 'selectpicker show-menu-arrow',
|
|
||||||
'data-none-selected-text' => lang('Common.none_selected_text'),
|
|
||||||
'data-selected-text-format' => 'count > 1',
|
|
||||||
'data-style' => 'btn-default btn-sm',
|
|
||||||
'data-width' => '100%'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.gcaptcha_enable'), 'gcaptcha_enable', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'gcaptcha_enable',
|
|
||||||
'id' => 'gcaptcha_enable',
|
|
||||||
'value' => 'gcaptcha_enable',
|
|
||||||
'checked' => $config['gcaptcha_enable'] == 1
|
|
||||||
]) ?>
|
|
||||||
<label class="control-label">
|
|
||||||
<a href="https://www.google.com/recaptcha/admin" target="_blank">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.gcaptcha_tooltip') ?>"></span>
|
|
||||||
</a>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.gcaptcha_site_key'), 'config_gcaptcha_site_key', ['class' => 'required control-label col-xs-2', 'id' => 'config_gcaptcha_site_key']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'gcaptcha_site_key',
|
|
||||||
'id' => 'gcaptcha_site_key',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['gcaptcha_site_key']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.gcaptcha_secret_key'), 'config_gcaptcha_secret_key', ['class' => 'required control-label col-xs-2', 'id' => 'config_gcaptcha_secret_key']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'gcaptcha_secret_key',
|
|
||||||
'id' => 'gcaptcha_secret_key',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['gcaptcha_secret_key']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.suggestions_layout'), 'suggestions_layout', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-10">
|
|
||||||
<div class="form-group form-group-sm row">
|
|
||||||
<div class="col-sm-3">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><?= lang('Config.suggestions_first_column') ?></span>
|
|
||||||
<?= form_dropdown(
|
|
||||||
'suggestions_first_column',
|
|
||||||
[
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'item_number' => lang('Items.number_information'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'cost_price' => lang('Items.cost_price')
|
|
||||||
],
|
|
||||||
$config['suggestions_first_column'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-3">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><?= lang('Config.suggestions_second_column') ?></span>
|
|
||||||
<?= form_dropdown(
|
|
||||||
'suggestions_second_column',
|
|
||||||
[
|
|
||||||
'' => lang('Config.none'),
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'item_number' => lang('Items.number_information'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'cost_price' => lang('Items.cost_price')
|
|
||||||
],
|
|
||||||
$config['suggestions_second_column'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-3">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><?= lang('Config.suggestions_third_column') ?></span>
|
|
||||||
<?= form_dropdown(
|
|
||||||
'suggestions_third_column',
|
|
||||||
[
|
|
||||||
'' => lang('Config.none'),
|
|
||||||
'name' => lang('Items.name'),
|
|
||||||
'item_number' => lang('Items.number_information'),
|
|
||||||
'unit_price' => lang('Items.unit_price'),
|
|
||||||
'cost_price' => lang('Items.cost_price')
|
|
||||||
],
|
|
||||||
$config['suggestions_third_column'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.giftcard_number'), 'giftcard_number', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'giftcard_number',
|
|
||||||
'value' => 'series',
|
|
||||||
'checked' => $config['giftcard_number'] == 'series'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.giftcard_series') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'giftcard_number',
|
|
||||||
'value' => 'random',
|
|
||||||
'checked' => $config['giftcard_number'] == 'random'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.giftcard_random') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.derive_sale_quantity'), 'derive_sale_quantity', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'derive_sale_quantity',
|
|
||||||
'id' => 'derive_sale_quantity',
|
|
||||||
'value' => 'derive_sale_quantity',
|
|
||||||
'checked' => $config['derive_sale_quantity'] == 1
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
<label class="control-label">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.derive_sale_quantity_tooltip') ?>"></span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.show_office_group'), 'show_office_group', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'show_office_group',
|
|
||||||
'id' => 'show_office_group',
|
|
||||||
'value' => 'show_office_group',
|
|
||||||
'checked' => $show_office_group > 0
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.multi_pack_enabled'), 'multi_pack_enabled', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'multi_pack_enabled',
|
|
||||||
'id' => 'multi_pack_enabled',
|
|
||||||
'value' => 'multi_pack_enabled',
|
|
||||||
'checked' => $config['multi_pack_enabled'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.include_hsn'), 'include_hsn', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'include_hsn',
|
|
||||||
'id' => 'include_hsn',
|
|
||||||
'value' => 'include_hsn',
|
|
||||||
'checked' => $config['include_hsn'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.category_dropdown'), 'category_dropdown', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'category_dropdown',
|
|
||||||
'id' => 'category_dropdown',
|
|
||||||
'value' => 'category_dropdown',
|
|
||||||
'checked' => $config['category_dropdown'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_general',
|
|
||||||
'id' => 'submit_general',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="lines_per_page" class="form-label"><?= lang('Config.lines_per_page'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-list"></i></span>
|
||||||
|
<input type="number" min="10" max="1000" name="lines_per_page" class="form-control" id="lines_per_page" value="<?= $config['lines_per_page']; ?>" required>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="enforce_privacy" name="enforce_privacy" <?= $config['enforce_privacy'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="enforce_privacy"><?= lang('Config.enforce_privacy'); ?></label>
|
||||||
|
<div class="form-text"><i class="bi bi-info-square pe-1"></i><?= lang('Config.enforce_privacy_tooltip') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receiving_calculate_average_price" name="receiving_calculate_average_price" <?= $config['receiving_calculate_average_price'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receiving_calculate_average_price"><?= lang('Config.receiving_calculate_average_price'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<label class="form-label"><?= lang('Config.image_restrictions'); ?></label>
|
||||||
|
<div class="col-12 col-sm-6 col-xl-3">
|
||||||
|
<div class="input-group mb-3" data-bs-toggle="tooltip" title="<?= lang('Config.image_max_width_tooltip'); ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrows"></i></span>
|
||||||
|
<input type="number" min="128" max="3840" name="image_max_width" id="image_max_width" class="form-control" value="<?= $config['image_max_width']; ?>" required>
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xl-3">
|
||||||
|
<div class="input-group mb-3" data-bs-toggle="tooltip" title="<?= lang('Config.image_max_height_tooltip'); ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrows-vertical"></i></span>
|
||||||
|
<input type="number" min="128" max="3840" name="image_max_height" id="image_max_height" class="form-control" value="<?= $config['image_max_height']; ?>" required>
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xl-3">
|
||||||
|
<div class="input-group mb-3" data-bs-toggle="tooltip" title="<?= lang('Config.image_max_size_tooltip'); ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-hdd"></i></span>
|
||||||
|
<input type="number" min="128" max="2048" name="image_max_size" id="image_max_size" class="form-control" value="<?= $config['image_max_size']; ?>" required>
|
||||||
|
<span class="input-group-text">kb</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-xl-9">
|
||||||
|
<div class="input-group mb-3" data-bs-toggle="tooltip" title="<?= lang('Config.image_allowed_file_types'); ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-images"></i></span>
|
||||||
|
<select name="image_allowed_types[]" id="image_allowed_types" class="form-select" multiple placeholder="<?= lang('Config.image_allowed_file_types'); ?>" required>
|
||||||
|
<?php foreach($image_allowed_types as $type): ?>
|
||||||
|
<option value="<?= $type; ?>" <?= in_array($type, $selected_image_allowed_types) ? 'selected' : ''; ?>>
|
||||||
|
<?= $type; ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" name="gcaptcha_enable" id="gcaptcha_enable" value="gcaptcha_enable" <?= $config['gcaptcha_enable'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="gcaptcha_enable"><?= lang('Config.gcaptcha_enable') ?></label>
|
||||||
|
<a class="d-inline-block" href="https://google.com/recaptcha/admin" target="_blank" rel="noopener"><i class="bi bi-link-45deg link-secondary"></i></a>
|
||||||
|
<div class="form-text"><i class="bi bi-info-square pe-1"></i><?= lang('Config.gcaptcha_tooltip') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row mb-3">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="gcaptcha_site_key" class="form-label"><?= lang('Config.gcaptcha_site_key') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-key"></i></span>
|
||||||
|
<input type="text" class="form-control" name="gcaptcha_site_key" id="gcaptcha_site_key" required>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="gcaptcha_secret_key" class="form-label"><?= lang('Config.gcaptcha_secret_key') ?></label>
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-stars"></i></span>
|
||||||
|
<input type="text" class="form-control" name="gcaptcha_secret_key" id="gcaptcha_secret_key" required>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row" id="suggestions_layout">
|
||||||
|
<label for="suggestions_layout" class="form-label"><?= lang('Config.suggestions_layout'); ?></label>
|
||||||
|
<div class="col-12 col-sm-6 col-xl-4 col-xxl-3 mb-3">
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-layout-three-columns"></i> 1.</span>
|
||||||
|
<select class="form-select" name="suggestions_first_column">
|
||||||
|
<option value="name" <?= $config['suggestions_first_column'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="item_number" <?= $config['suggestions_first_column'] == 'item_number' ? 'selected' : '' ?>><?= lang('Items.number_information') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['suggestions_first_column'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['suggestions_first_column'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xl-4 col-xxl-3 mb-3">
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-layout-three-columns"></i> 2.</span>
|
||||||
|
<select class="form-select" name="suggestions_second_column">
|
||||||
|
<option value="" <?= $config['suggestions_second_column'] == null ? 'selected' : '' ?>><?= lang('Config.none') ?></option>
|
||||||
|
<option value="name" <?= $config['suggestions_second_column'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="item_number" <?= $config['suggestions_second_column'] == 'item_number' ? 'selected' : '' ?>><?= lang('Items.number_information') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['suggestions_second_column'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['suggestions_second_column'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xl-4 col-xxl-3 mb-3">
|
||||||
|
<div class="input-group">
|
||||||
|
<span class="input-group-text"><i class="bi bi-layout-three-columns"></i> 3.</span>
|
||||||
|
<select class="form-select" name="suggestions_third_column">
|
||||||
|
<option value="" <?= $config['suggestions_third_column'] == null ? 'selected' : '' ?>><?= lang('Config.none') ?></option>
|
||||||
|
<option value="name" <?= $config['suggestions_third_column'] == 'name' ? 'selected' : '' ?>><?= lang('Items.name') ?></option>
|
||||||
|
<option value="item_number" <?= $config['suggestions_third_column'] == 'item_number' ? 'selected' : '' ?>><?= lang('Items.number_information') ?></option>
|
||||||
|
<option value="unit_price" <?= $config['suggestions_third_column'] == 'unit_price' ? 'selected' : '' ?>><?= lang('Items.unit_price') ?></option>
|
||||||
|
<option value="cost_price" <?= $config['suggestions_third_column'] == 'cost_price' ? 'selected' : '' ?>><?= lang('Items.cost_price') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="giftcard_number" class="form-label"><?= lang('Config.giftcard_number'); ?></label>
|
||||||
|
<div class="mb-3">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="giftcard_number" id="giftcard_series" value="series" <?= $config['giftcard_number'] == 'series' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="giftcard_series"><?= lang('Config.giftcard_series') ?></label>
|
||||||
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="giftcard_number" id="giftcard_random" value="random" <?= $config['giftcard_number'] == 'random' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="giftcard_random"><?= lang('Config.giftcard_random') ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="derive_sale_quantity" name="derive_sale_quantity" value="derive_sale_quantity" <?= $config['derive_sale_quantity'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="derive_sale_quantity"><?= lang('Config.derive_sale_quantity'); ?></label>
|
||||||
|
<div class="form-text"><i class="bi bi-info-square pe-1"></i><?= lang('Config.derive_sale_quantity_tooltip') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="show_office_group" name="show_office_group" value="show_office_group" <?= $show_office_group > 0 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="show_office_group"><?= lang('Config.show_office_group'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="multi_pack_enabled" name="multi_pack_enabled" value="multi_pack_enabled" <?= $config['multi_pack_enabled'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="multi_pack_enabled"><?= lang('Config.multi_pack_enabled'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="include_hsn" name="include_hsn" value="include_hsn" <?= $config['include_hsn'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="include_hsn"><?= lang('Config.include_hsn'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="category_dropdown" name="category_dropdown" value="category_dropdown" <?= $config['category_dropdown'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="category_dropdown"><?= lang('Config.category_dropdown'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_general"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -484,7 +234,7 @@
|
|||||||
|
|
||||||
$('#general_config_form').validate($.extend(form_support.handler, {
|
$('#general_config_form').validate($.extend(form_support.handler, {
|
||||||
|
|
||||||
errorLabelContainer: "#general_error_message_box",
|
errorLabelContainer: ".general_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
lines_per_page: {
|
lines_per_page: {
|
||||||
@@ -528,6 +278,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -540,4 +291,11 @@
|
|||||||
}
|
}
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
|
|
||||||
|
new TomSelect('#image_allowed_types', {
|
||||||
|
plugins: ['checkbox_options', 'remove_button'],
|
||||||
|
placeholder: '<?= lang('Common.none_selected_text') ?>',
|
||||||
|
hidePlaceholder: true,
|
||||||
|
closeAfterSelect: false,
|
||||||
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -6,152 +6,110 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveInfo/', ['id' => 'info_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveInfo/', ['id' => 'info_config_form', 'enctype' => 'multipart/form-data', 'class' => 'needs-validation']) ?> <!-- TODO-BS5 add is-invalid and invalid-feeback from BS5 to boxes -->
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="info_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.info_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="info_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.company'), 'company', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-6">
|
<div class="row">
|
||||||
<div class="input-group">
|
<div class="col-12 col-lg-6">
|
||||||
<span class="input-group-addon input-sm">
|
<label for="info-company" class="form-label"><?= lang('Config.company'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<span class="glyphicon glyphicon-home"></span>
|
<div class="input-group mb-3">
|
||||||
</span>
|
<span class="input-group-text"><i class="bi bi-shop-window"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="company" id="info-company" value="<?= $config['company']; ?>" required> <!-- TODO-BS5 invalid-feedback makes input borders not rounded? -->
|
||||||
'name' => 'company',
|
<div class="invalid-feedback"><?= lang('Config.company_required') ?></div>
|
||||||
'id' => 'company',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['company']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.company_logo'), 'company_logo', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="fileinput <?= $logo_exists ? 'fileinput-exists' : 'fileinput-new' ?>" data-provides="fileinput">
|
|
||||||
<div class="fileinput-new thumbnail" style="width: 200px; height: 200px;"></div>
|
|
||||||
<div class="fileinput-preview fileinput-exists thumbnail" style="max-width: 200px; max-height: 200px;">
|
|
||||||
<img data-src="holder.js/100%x100%" alt="<?= esc(lang('Config.company_logo')) ?>" src="<?= $logo_src ?>" style="max-height: 100%; max-width: 100%;">
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span class="btn btn-default btn-sm btn-file">
|
|
||||||
<span class="fileinput-new"><?= lang('Config.company_select_image') ?></span>
|
|
||||||
<span class="fileinput-exists"><?= lang('Config.company_change_image') ?></span>
|
|
||||||
<input type="file" name="company_logo">
|
|
||||||
</span>
|
|
||||||
<a href="#" class="btn btn-default btn-sm fileinput-exists" data-dismiss="fileinput"><?= lang('Config.company_remove_image') ?></a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.address'), 'address', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'address',
|
|
||||||
'id' => 'address',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['address']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.website'), 'website', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-globe"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'website',
|
|
||||||
'id' => 'website',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['website']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Common.email'), 'email', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-envelope"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'email',
|
|
||||||
'id' => 'email',
|
|
||||||
'type' => 'email',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['email']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.phone'), 'phone', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-phone-alt"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'phone',
|
|
||||||
'id' => 'phone',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['phone']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.fax'), 'fax', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-phone-alt"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'fax',
|
|
||||||
'id' => 'fax',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['fax']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Common.return_policy'), 'return_policy', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'return_policy',
|
|
||||||
'id' => 'return_policy',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['return_policy']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_info',
|
|
||||||
'id' => 'submit_info',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row mb-3">
|
||||||
|
<label for="info-company_logo" class="form-label"><?= lang('Config.company_logo'); ?></label>
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<div id="info-company_logo" class="w-100 fileinput <?= $logo_exists ? 'fileinput-exists' : 'fileinput-new'; ?>" data-provides="fileinput">
|
||||||
|
<div class="input-group mb-3" aria-describedby="company-logo-desc">
|
||||||
|
<span class="input-group-text"><i class="bi bi-image"></i></span>
|
||||||
|
<div class="fileinput-new form-control rounded-end mb-0" style="height: 200px; cursor: default;"></div>
|
||||||
|
<div class="fileinput-exists fileinput-preview img-thumbnail form-control rounded-end mb-0 bg-light mh-100" style="height: 200px; cursor: default; background-size: 40px 40px; background-position: 0 0, 20px 20px; background-image: linear-gradient(45deg, white 25%, transparent 25%, transparent 75%, white 75%, white), linear-gradient(45deg, white 25%, transparent 25%, transparent 75%, white 75%, white);">
|
||||||
|
<img class="mh-100 mw-100" data-src="holder.js/100%x100%" alt="<?= esc(lang('Config.company_logo')) ?>" src="<?= $logo_src ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div type="button" class="btn btn-secondary btn-file me-2">
|
||||||
|
<span class="fileinput-new"><i class="bi bi-hand-index me-2"></i><?= lang('Config.company_select_image') ?></span>
|
||||||
|
<span class="fileinput-exists"><i class="bi bi-images me-2"></i><?= lang('Config.company_change_image') ?></span>
|
||||||
|
<input type="file" name="company_logo">
|
||||||
|
</div>
|
||||||
|
<a type="button" class="btn btn-outline-secondary fileinput-exists" data-dismiss="fileinput">
|
||||||
|
<i class="bi bi-eraser me-2"></i><?= lang('Config.company_remove_image') ?>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="col-12 col-lg-6 form-text d-none d-lg-block" id="company-logo-desc">
|
||||||
|
<ul class="list-unstyled">
|
||||||
|
<li>» Supported file formats; gif, png, jpg</li> <!-- TODO-BS5 add to translations -->
|
||||||
|
<li>» Max upload size of 100kb</li> <!-- TODO-BS5 add to translations -->
|
||||||
|
<li>» Max dimensions of 200x200px</li> <!-- TODO-BS5 add to translations -->
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="info-address" class="form-label"><?= lang('Config.address'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-house"></i></span>
|
||||||
|
<textarea class="form-control" name="address" id="info-address" rows="10" required><?= $config['address']; ?></textarea>
|
||||||
|
<div class="invalid-feedback"><?= lang('Config.address_required') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="info-website" class="form-label"><?= lang('Config.website'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-globe"></i></span>
|
||||||
|
<input class="form-control" name="website" id="info-website" value="<?= $config['website']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="info-email" class="form-label"><?= lang('Config.email'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-at"></i></span>
|
||||||
|
<input type="email" class="form-control" name="email" id="info-email" value="<?= $config['email']; ?>">
|
||||||
|
<div class="invalid-feedback"><?= lang('Common.email_invalid_format') ?></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="info-phone" class="form-label"><?= lang('Config.phone'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-telephone"></i></span>
|
||||||
|
<input type="tel" class="form-control" name="phone" id="info-phone" value="<?= $config['phone']; ?>" required>
|
||||||
|
<div class="invalid-feedback"><?= lang('Config.phone_required') ?></div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="info-fax" class="form-label"><?= lang('Config.fax'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-printer"></i></span>
|
||||||
|
<input type="tel" class="form-control" name="fax" id="info-fax" value="<?= $config['fax']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="info-return_policy" class="form-label"><?= lang('Common.return_policy'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-box-arrow-in-down-left"></i></span>
|
||||||
|
<textarea class="form-control" name="return_policy" id="info-return_policy" rows="10" required><?= $config['return_policy']; ?></textarea>
|
||||||
|
<div class="invalid-feedback"><?= lang('Config.return_policy_required') ?></div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_info"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -167,7 +125,7 @@
|
|||||||
|
|
||||||
$('#info_config_form').validate($.extend(form_support.handler, {
|
$('#info_config_form').validate($.extend(form_support.handler, {
|
||||||
|
|
||||||
errorLabelContainer: "#info_error_message_box",
|
errorLabelContainer: ".info_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
company: "required",
|
company: "required",
|
||||||
|
|||||||
@@ -5,64 +5,55 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveMailchimp/', ['id' => 'mailchimp_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveMailchimp/', ['id' => 'mailchimp_config_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<div id="integrations_header"><?= lang('Config.mailchimp_configuration') ?></div>
|
$title_info['config_title'] = lang('Config.integrations_configuration');
|
||||||
<ul id="mailchimp_error_message_box" class="error_message_box"></ul>
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<legend class="fs-5"><?= lang('Config.mailchimp_configuration') ?></legend>
|
||||||
<?= form_label(lang('Config.mailchimp_api_key'), 'mailchimp_api_key', ['class' => 'control-label col-xs-2']) ?>
|
<ul id="error_message_box" class="mailchimp_error_message_box alert alert-warning d-none"></ul>
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group">
|
<div class="row">
|
||||||
<span class="input-group-addon input-sm">
|
<div class="col-12 col-lg-6">
|
||||||
<span class="glyphicon glyphicon-cloud"></span>
|
<label for="mailchimp_api_key" class="form-label">
|
||||||
</span>
|
<?= lang('Config.mailchimp_api_key'); ?>
|
||||||
<?= form_input([
|
<!--<a href="https://eepurl.com/dyijVH" target="_blank" rel="noopener">
|
||||||
'name' => 'mailchimp_api_key',
|
<i class="bi bi-info-circle-fill text-secondary" data-bs-toggle="tooltip" title="<?= lang('Config.mailchimp_tooltip'); ?>"></i>
|
||||||
'id' => 'mailchimp_api_key',
|
</a>-->
|
||||||
'class' => 'form-control input-sm',
|
</label>
|
||||||
'value' => $mailchimp['api_key']
|
<div class="input-group">
|
||||||
]) ?>
|
<span class="input-group-text" id="mailchimp-api-key-icon"><i class="bi bi-key"></i></span>
|
||||||
</div>
|
<input type="text" class="form-control" name="mailchimp_api_key" id="mailchimp_api_key" aria-describedby="mailchimp-api-key-icon" value="<?= $mailchimp['api_key']; ?>">
|
||||||
</div>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<label class="control-label">
|
|
||||||
<a href="https://eepurl.com/b9a05b" target="_blank">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.mailchimp_tooltip') ?>"></span>
|
|
||||||
</a>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-text mb-3">
|
||||||
<div class="form-group form-group-sm">
|
<a class="link-secondary" href="https://eepurl.com/dyijVH" target="_blank" rel="noopener">
|
||||||
<?= form_label(lang('Config.mailchimp_lists'), 'mailchimp_list_id', ['class' => 'control-label col-xs-2']) ?>
|
<i class="bi bi-info-square pe-1"></i><?= lang('Config.mailchimp_tooltip') ?>
|
||||||
<div class="col-xs-4">
|
</a>
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm">
|
|
||||||
<span class="glyphicon glyphicon-user"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_dropdown(
|
|
||||||
'mailchimp_list_id',
|
|
||||||
$mailchimp['lists'],
|
|
||||||
$mailchimp['list_id'],
|
|
||||||
'id="mailchimp_list_id" class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_submit([
|
<div class="col-12 col-lg-6">
|
||||||
'name' => 'submit_mailchimp',
|
<label for="mailchimp_list_id" class="form-label"><?= lang('Config.mailchimp_lists'); ?></label>
|
||||||
'id' => 'submit_mailchimp',
|
<div class="input-group mb-3">
|
||||||
'value' => lang('Common.submit'),
|
<span class="input-group-text" id="mailchimp-lists-icon"><i class="bi bi-list-stars"></i></span>
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
<select class="form-select" id="mailchimp_list_id" aria-describedby="mailchimp-lists-icon" <?= $mailchimp['api_key'] == null ? 'disabled' : '' ?>>
|
||||||
]) ?>
|
<option>Choose...</option>
|
||||||
|
<?php foreach($mailchimp['lists'] as $value => $display_text): ?>
|
||||||
</fieldset>
|
<option value="<?= $value; ?>" <?= $value == $mailchimp['list_id'] ? 'selected' : ''; ?>>
|
||||||
|
<?= $display_text; ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="sumbit_mailchimp"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -74,6 +65,7 @@
|
|||||||
},
|
},
|
||||||
function(response) {
|
function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -102,7 +94,7 @@
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: '#mailchimp_error_message_box'
|
errorLabelContainer: '.mailchimp_error_message_box'
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -6,193 +6,135 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveInvoice/', ['id' => 'invoice_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveInvoice/', ['id' => 'invoice_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="invoice_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.invoice_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="invoice_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.invoice_enable'), 'invoice_enable', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'invoice_enable',
|
|
||||||
'value' => 'invoice_enable',
|
|
||||||
'id' => 'invoice_enable',
|
|
||||||
'checked' => $config['invoice_enable'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="form-check form-switch mb-3">
|
||||||
<?= form_label(lang('Config.invoice_type'), 'invoice_type', ['class' => 'control-label col-xs-2']) ?>
|
<input class="form-check-input" type="checkbox" role="switch" id="invoice_enable" name="invoice_enable" value="invoice_enable" <?= $config['invoice_enable'] == 1 ? 'checked' : '' ?>>
|
||||||
<div class="col-xs-3">
|
<label class="form-check-label" for="invoice_enable"><?= lang('Config.invoice_enable'); ?></label>
|
||||||
<?= form_dropdown(
|
|
||||||
'invoice_type',
|
|
||||||
$invoice_type_options,
|
|
||||||
$config['invoice_type'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.recv_invoice_format'), 'recv_invoice_format', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'recv_invoice_format',
|
|
||||||
'id' => 'recv_invoice_format',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['recv_invoice_format']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.invoice_default_comments'), 'invoice_default_comments', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-5">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'invoice_default_comments',
|
|
||||||
'id' => 'invoice_default_comments',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['invoice_default_comments']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.invoice_email_message'), 'invoice_email_message', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-5">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'invoice_email_message',
|
|
||||||
'id' => 'invoice_email_message',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['invoice_email_message']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.line_sequence'), 'line_sequence', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'line_sequence',
|
|
||||||
$line_sequence_options,
|
|
||||||
$config['line_sequence'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.sales_invoice_format'), 'sales_invoice_format', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'sales_invoice_format',
|
|
||||||
'id' => 'sales_invoice_format',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['sales_invoice_format']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.last_used_invoice_number'), 'last_used_invoice_number', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'name' => 'last_used_invoice_number',
|
|
||||||
'id' => 'last_used_invoice_number',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['last_used_invoice_number']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.sales_quote_format'), 'sales_quote_format', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'sales_quote_format',
|
|
||||||
'id' => 'sales_quote_format',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['sales_quote_format']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.last_used_quote_number'), 'last_used_quote_number', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'name' => 'last_used_quote_number',
|
|
||||||
'id' => 'last_used_quote_number',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['last_used_quote_number']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.quote_default_comments'), 'quote_default_comments', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-5">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'quote_default_comments',
|
|
||||||
'id' => 'quote_default_comments',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['quote_default_comments']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.work_order_enable'), 'work_order_enable', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'work_order_enable',
|
|
||||||
'value' => 'work_order_enable',
|
|
||||||
'id' => 'work_order_enable',
|
|
||||||
'checked' => $config['work_order_enable'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.work_order_format'), 'work_order_format', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'work_order_format',
|
|
||||||
'id' => 'work_order_format',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['work_order_format']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.last_used_work_order_number'), 'last_used_work_order_number', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'name' => 'last_used_work_order_number',
|
|
||||||
'id' => 'last_used_work_order_number',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['last_used_work_order_number']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_invoice',
|
|
||||||
'id' => 'submit_invoice',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="invoice_type" class="form-label"><?= lang('Config.invoice_type'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-file-code"></i></span>
|
||||||
|
<select class="form-select" name="invoice_type">
|
||||||
|
<?php foreach ($invoice_type_options as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $key == $config['invoice_type'] ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="recv_invoice_format" class="form-label"><?= lang('Config.recv_invoice_format'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
|
<input type="text" class="form-control" name="recv_invoice_format" id="recv_invoice_format" value="<?= $config['recv_invoice_format']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="invoice_default_comments" class="form-label"><?= lang('Config.invoice_default_comments'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-file-text"></i></span>
|
||||||
|
<textarea class="form-control" name="invoice_default_comments" id="invoice_default_comments" rows="10" required><?= $config['invoice_default_comments']; ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="invoice_email_message" class="form-label"><?= lang('Config.invoice_email_message'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-envelope-paper"></i></span>
|
||||||
|
<textarea class="form-control" name="invoice_email_message" id="invoice_email_message" rows="10" required><?= $config['invoice_email_message']; ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="line_sequence" class="form-label"><?= lang('Config.line_sequence'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-list-ol"></i></span>
|
||||||
|
<select class="form-select" name="line_sequence">
|
||||||
|
<?php foreach ($line_sequence_options as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $key == $config['line_sequence'] ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="sales_invoice_format" class="form-label"><?= lang('Config.sales_invoice_format'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
|
<input type="text" class="form-control" name="sales_invoice_format" id="sales_invoice_format" value="<?= $config['sales_invoice_format']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="last_used_invoice_number" class="form-label"><?= lang('Config.last_used_invoice_number'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="number" class="form-control" name="last_used_invoice_number" id="last_used_invoice_number" value="<?= $config['last_used_invoice_number']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="sales_quote_format" class="form-label"><?= lang('Config.sales_quote_format'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
|
<input type="text" class="form-control" name="sales_quote_format" id="sales_quote_format" value="<?= $config['sales_quote_format']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="last_used_quote_number" class="form-label"><?= lang('Config.last_used_quote_number'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="number" class="form-control" name="last_used_quote_number" id="last_used_quote_number" value="<?= $config['last_used_quote_number']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="quote_default_comments" class="form-label"><?= lang('Config.quote_default_comments'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-file-text"></i></span>
|
||||||
|
<textarea class="form-control" name="quote_default_comments" id="quote_default_comments" rows="10" required><?= $config['quote_default_comments']; ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="work_order_enable" name="work_order_enable" value="work_order_enable" <?= $config['work_order_enable'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="work_order_enable"><?= lang('Config.work_order_enable'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="work_order_format" class="form-label"><?= lang('Config.work_order_format'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-braces"></i></span>
|
||||||
|
<input type="text" class="form-control" name="work_order_format" id="work_order_format" value="<?= $config['work_order_format']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="last_used_work_order_number" class="form-label"><?= lang('Config.last_used_work_order_number'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="number" class="form-control" name="last_used_work_order_number" id="last_used_work_order_number" value="<?= $config['last_used_work_order_number']; ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_invoice"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -225,7 +167,7 @@
|
|||||||
|
|
||||||
$("#invoice_config_form").validate($.extend(form_support.handler, {
|
$("#invoice_config_form").validate($.extend(form_support.handler, {
|
||||||
|
|
||||||
errorLabelContainer: "#invoice_error_message_box",
|
errorLabelContainer: ".invoice_error_message_box",
|
||||||
|
|
||||||
submitHandler: function(form) {
|
submitHandler: function(form) {
|
||||||
$(form).ajaxSubmit({
|
$(form).ajaxSubmit({
|
||||||
@@ -235,6 +177,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
|
|||||||
@@ -4,29 +4,25 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('', ['id' => 'license_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('', ['id' => 'license_config_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset>
|
|
||||||
|
|
||||||
<?php
|
<?php
|
||||||
$counter = 0;
|
$title_info['config_title'] = lang('Config.license_configuration');
|
||||||
foreach ($licenses as $license) {
|
echo view('configs/config_header', $title_info);
|
||||||
?>
|
?>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label($license['title'], 'license', ['class' => 'control-label col-xs-3']) ?>
|
<?php
|
||||||
<div class="col-xs-6">
|
$license_i = 0;
|
||||||
<?= form_textarea([
|
foreach ($licenses as $license) {
|
||||||
'name' => 'license',
|
?>
|
||||||
'id' => 'license_' . $counter++, // TODO: String Interpolation
|
|
||||||
'class' => 'form-control font-monospace',
|
<div class="mb-3 mx-3 mx-lg-0">
|
||||||
'rows' => '14',
|
<label for="license_<?= $license_i; ?>" class="form-label"><?= $license['title']; ?></label>
|
||||||
'readonly' => '',
|
<textarea name="license" rows="10" id="license_<?= $license_i; ?>" class="form-control font-monospace" style="font-size: .875rem;" readonly><?= $license['text']; ?></textarea>
|
||||||
'value' => $license['text']
|
</div>
|
||||||
]) ?>
|
|
||||||
</div>
|
<?php
|
||||||
</div>
|
$license_i++; // Increment counter
|
||||||
<?php } ?>
|
} ?>
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|||||||
@@ -5,285 +5,245 @@
|
|||||||
* @var string $controller_name
|
* @var string $controller_name
|
||||||
* @var array $config
|
* @var array $config
|
||||||
*/
|
*/
|
||||||
|
|
||||||
|
$beta = '<sup><span class="badge bg-secondary">BETA</span></sup>';
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveLocale/', ['id' => 'locale_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveLocale/', ['id' => 'locale_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="locale_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.locale_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="locale_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.number_locale'), 'number_locale', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
<div class="row">
|
||||||
<?= form_input([
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
'name' => 'number_locale',
|
<label for="number_locale" class="form-label"><?= lang('Config.number_locale') ?></label>
|
||||||
'id' => 'number_locale',
|
<div class="input-group mb-3">
|
||||||
'class' => 'form-control input-sm',
|
<span class="input-group-text"><i class="bi bi-globe-americas"></i></span>
|
||||||
'value' => $config['number_locale']
|
<input type="text" class="form-control" name="number_locale" id="number_locale" value="<?= $config['number_locale'] ?>">
|
||||||
]) ?>
|
|
||||||
<?= form_hidden(['name' => 'save_number_locale', 'value' => $config['number_locale']]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<label class="control-label">
|
|
||||||
<a href="https://github.com/opensourcepos/opensourcepos/wiki/Localisation-support" target="_blank">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.number_locale_tooltip') ?>"></span>
|
|
||||||
</a>
|
|
||||||
<span id="number_locale_example">
|
|
||||||
<?= to_currency(1234567890.12300) ?>
|
|
||||||
</span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
<?= form_label(lang('Config.thousands_separator'), 'thousands_separator', ['class' => 'control-label col-xs-2']) ?>
|
<label for="number_locale_example" class="form-label">Localization Example</label>
|
||||||
<div class="col-xs-2">
|
<div class="mb-3" id="number_locale_example">
|
||||||
<?= form_checkbox([
|
<?= to_currency(1234567890.12300) ?>
|
||||||
'name' => 'thousands_separator',
|
<a href="https://github.com/opensourcepos/opensourcepos/wiki/Localisation-support" target="_blank" rel="noopener">
|
||||||
'id' => 'thousands_separator',
|
<i class="bi bi-link-45deg link-secondary" data-bs-toggle="tooltip" title="<?= lang('Config.number_locale_tooltip'); ?>"></i>
|
||||||
'value' => 'thousands_separator',
|
</a>
|
||||||
'checked' => $config['thousands_separator'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.currency_symbol'), 'currency_symbol', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'currency_symbol',
|
|
||||||
'id' => 'currency_symbol',
|
|
||||||
'class' => 'form-control input-sm number_locale',
|
|
||||||
'value' => $config['currency_symbol']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.currency_code'), 'currency_code', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'currency_code',
|
|
||||||
'id' => 'currency_code',
|
|
||||||
'class' => 'form-control input-sm number_locale',
|
|
||||||
'value' => $currency_code
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.currency_decimals'), 'currency_decimals', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'currency_decimals',
|
|
||||||
[
|
|
||||||
'0' => '0',
|
|
||||||
'1' => '1',
|
|
||||||
'2' => '2'
|
|
||||||
],
|
|
||||||
$config['currency_decimals'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.tax_decimals'), 'tax_decimals', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'tax_decimals',
|
|
||||||
[
|
|
||||||
'0' => '0',
|
|
||||||
'1' => '1',
|
|
||||||
'2' => '2',
|
|
||||||
'3' => '3',
|
|
||||||
'4' => '4'
|
|
||||||
],
|
|
||||||
$config['tax_decimals'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.quantity_decimals'), 'quantity_decimals', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'quantity_decimals',
|
|
||||||
[
|
|
||||||
'0' => '0',
|
|
||||||
'1' => '1',
|
|
||||||
'2' => '2',
|
|
||||||
'3' => '3'
|
|
||||||
],
|
|
||||||
$config['quantity_decimals'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.cash_decimals'), 'cash_decimals', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'cash_decimals',
|
|
||||||
[
|
|
||||||
'-1' => '-1',
|
|
||||||
'0' => '0',
|
|
||||||
'1' => '1',
|
|
||||||
'2' => '2'
|
|
||||||
],
|
|
||||||
$config['cash_decimals'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<label class="control-label">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.cash_decimals_tooltip') ?>"></span>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.cash_rounding'), 'cash_rounding_code', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'cash_rounding_code',
|
|
||||||
$rounding_options,
|
|
||||||
$config['cash_rounding_code'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.payment_options_order'), 'payment_options_order', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'payment_options_order',
|
|
||||||
[
|
|
||||||
'cashdebitcredit' => lang('Sales.cash') . ' / ' . lang('Sales.debit') . ' / ' . lang('Sales.credit'),
|
|
||||||
'debitcreditcash' => lang('Sales.debit') . ' / ' . lang('Sales.credit') . ' / ' . lang('Sales.cash'),
|
|
||||||
'debitcashcredit' => lang('Sales.debit') . ' / ' . lang('Sales.cash') . ' / ' . lang('Sales.credit'),
|
|
||||||
'creditdebitcash' => lang('Sales.credit') . ' / ' . lang('Sales.debit') . ' / ' . lang('Sales.cash'),
|
|
||||||
'creditcashdebit' => lang('Sales.credit') . ' / ' . lang('Sales.cash') . ' / ' . lang('Sales.debit')
|
|
||||||
],
|
|
||||||
$config['payment_options_order'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.country_codes'), 'country_codes', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'country_codes',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['country_codes']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<label class="control-label">
|
|
||||||
<a href="https://wiki.openstreetmap.org/wiki/Nominatim/Country_Codes" target="_blank">
|
|
||||||
<span class="glyphicon glyphicon-info-sign" data-toggle="tooltip" data-placement="right" title="<?= lang('Config.country_codes_tooltip'); ?>"></span>
|
|
||||||
</a>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.language'), 'language', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'language',
|
|
||||||
get_languages(),
|
|
||||||
current_language_code(true) . ':' . current_language(true),
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.timezone'), 'timezone', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'timezone',
|
|
||||||
get_timezones(),
|
|
||||||
$config['timezone'] ? $config['timezone'] : date_default_timezone_get(),
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.datetimeformat'), 'datetimeformat', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'dateformat',
|
|
||||||
get_dateformats(),
|
|
||||||
$config['dateformat'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-sm-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'timeformat',
|
|
||||||
get_timeformats(),
|
|
||||||
$config['timeformat'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.date_or_time_format'), 'date_or_time_format', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'date_or_time_format',
|
|
||||||
'id' => 'date_or_time_format',
|
|
||||||
'value' => 'date_or_time_format',
|
|
||||||
'checked' => $config['date_or_time_format'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.financial_year'), 'financial_year', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'financial_year',
|
|
||||||
[
|
|
||||||
'1' => lang('Config.financial_year_jan'),
|
|
||||||
'2' => lang('Config.financial_year_feb'),
|
|
||||||
'3' => lang('Config.financial_year_mar'),
|
|
||||||
'4' => lang('Config.financial_year_apr'),
|
|
||||||
'5' => lang('Config.financial_year_may'),
|
|
||||||
'6' => lang('Config.financial_year_jun'),
|
|
||||||
'7' => lang('Config.financial_year_jul'),
|
|
||||||
'8' => lang('Config.financial_year_aug'),
|
|
||||||
'9' => lang('Config.financial_year_sep'),
|
|
||||||
'10' => lang('Config.financial_year_oct'),
|
|
||||||
'11' => lang('Config.financial_year_nov'),
|
|
||||||
'12' => lang('Config.financial_year_dec')
|
|
||||||
],
|
|
||||||
$config['financial_year'],
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_locale',
|
|
||||||
'id' => 'submit_locale',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="thousands_separator" name="thousands_separator" value="thousands_separator" <?= $config['thousands_separator'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="thousands_separator"><?= lang('Config.thousands_separator'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="currency_symbol" class="form-label"><?= lang('Config.currency_symbol') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-currency-exchange"></i></span>
|
||||||
|
<input type="text" class="form-control" name="currency_symbol" id="currency_symbol" value="<?= $config['currency_symbol'] ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="currency_code" class="form-label"><?= lang('Config.currency_code') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-cash"></i></span>
|
||||||
|
<input type="text" class="form-control" name="currency_code" id="currency_code" value="<?= $currency_code ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="currency_decimals" class="form-label"><?= lang('Config.currency_decimals') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-coin"></i></span>
|
||||||
|
<select class="form-select" name="currency_decimals" id="currency_decimals">
|
||||||
|
<option value="0" <?= $config['currency_decimals'] == '0' ? 'selected' : '' ?>>0</option>
|
||||||
|
<option value="1" <?= $config['currency_decimals'] == '1' ? 'selected' : '' ?>>1</option>
|
||||||
|
<option value="2" <?= $config['currency_decimals'] == '2' ? 'selected' : '' ?>>2</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="tax_decimals" class="form-label"><?= lang('Config.tax_decimals') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-archive"></i></span>
|
||||||
|
<select class="form-select" name="tax_decimals" id="tax_decimals">
|
||||||
|
<option value="0" <?= $config['tax_decimals'] == '0' ? 'selected' : '' ?>>0</option>
|
||||||
|
<option value="1" <?= $config['tax_decimals'] == '1' ? 'selected' : '' ?>>1</option>
|
||||||
|
<option value="2" <?= $config['tax_decimals'] == '2' ? 'selected' : '' ?>>2</option>
|
||||||
|
<option value="3" <?= $config['tax_decimals'] == '3' ? 'selected' : '' ?>>3</option>
|
||||||
|
<option value="4" <?= $config['tax_decimals'] == '4' ? 'selected' : '' ?>>4</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="quantity_decimals" class="form-label"><?= lang('Config.quantity_decimals') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-123"></i></span>
|
||||||
|
<select class="form-select" name="quantity_decimals" id="quantity_decimals">
|
||||||
|
<option value="0" <?= $config['quantity_decimals'] == '0' ? 'selected' : '' ?>>0</option>
|
||||||
|
<option value="1" <?= $config['quantity_decimals'] == '1' ? 'selected' : '' ?>>1</option>
|
||||||
|
<option value="2" <?= $config['quantity_decimals'] == '2' ? 'selected' : '' ?>>2</option>
|
||||||
|
<option value="3" <?= $config['quantity_decimals'] == '3' ? 'selected' : '' ?>>3</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="cash_decimals" class="form-label"><?= lang('Config.cash_decimals') ?>
|
||||||
|
<i class="bi bi-info-circle-fill text-secondary" data-bs-toggle="tooltip" title="<?= lang('Config.cash_decimals_tooltip'); ?>"></i>
|
||||||
|
</label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-cash-coin"></i></span>
|
||||||
|
<select class="form-select" name="cash_decimals" id="cash_decimals">
|
||||||
|
<option value="0" <?= $config['cash_decimals'] == '0' ? 'selected' : '' ?>>0</option>
|
||||||
|
<option value="1" <?= $config['cash_decimals'] == '1' ? 'selected' : '' ?>>1</option>
|
||||||
|
<option value="2" <?= $config['cash_decimals'] == '2' ? 'selected' : '' ?>>2</option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-sm-6 col-xxl-3">
|
||||||
|
<label for="cash_rounding_code" class="form-label"><?= lang('Config.cash_rounding') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-repeat"></i></span>
|
||||||
|
<select class="form-select" name="cash_rounding_code" id="cash_rounding_code">
|
||||||
|
<?php foreach ($rounding_options as $code => $label): ?>
|
||||||
|
<option value="<?= $code ?>" <?= $config['cash_rounding_code'] == $code ? 'selected' : '' ?>><?= $label ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="payment_options_order" class="form-label"><?= lang('Config.payment_options_order') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-credit-card"></i></span>
|
||||||
|
<select class="form-select" name="payment_options_order" id="payment_options_order">
|
||||||
|
<option value="cashdebitcredit" <?= $config['payment_options_order'] == 'cashdebitcredit' ? 'selected' : '' ?>><?= lang('Sales.cash') ?> / <?= lang('Sales.debit') ?> / <?= lang('Sales.credit') ?></option>
|
||||||
|
<option value="debitcreditcash" <?= $config['payment_options_order'] == 'debitcreditcash' ? 'selected' : '' ?>><?= lang('Sales.debit') ?> / <?= lang('Sales.credit') ?> / <?= lang('Sales.cash') ?></option>
|
||||||
|
<option value="debitcashcredit" <?= $config['payment_options_order'] == 'debitcashcredit' ? 'selected' : '' ?>><?= lang('Sales.debit') ?> / <?= lang('Sales.cash') ?> / <?= lang('Sales.credit') ?></option>
|
||||||
|
<option value="creditdebitcash" <?= $config['payment_options_order'] == 'creditdebitcash' ? 'selected' : '' ?>><?= lang('Sales.credit') ?> / <?= lang('Sales.debit') ?> / <?= lang('Sales.cash') ?></option>
|
||||||
|
<option value="creditcashdebit" <?= $config['payment_options_order'] == 'creditcashdebit' ? 'selected' : '' ?>><?= lang('Sales.credit') ?> / <?= lang('Sales.cash') ?> / <?= lang('Sales.debit') ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="country_codes" class="form-label">
|
||||||
|
<?= lang('Config.country_codes') ?>
|
||||||
|
<a href="https://wiki.openstreetmap.org/wiki/Nominatim/Country_Codes" target="_blank" rel="noopener">
|
||||||
|
<i class="bi bi-link-45deg text-secondary" data-bs-toggle="tooltip" title="<?= lang('Config.country_codes_tooltip'); ?>"></i>
|
||||||
|
</a>
|
||||||
|
</label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-code"></i></span>
|
||||||
|
<input type="text" class="form-control" name="country_codes" id="country_codes" value="<?= $config['country_codes'] ?>">
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="language" class="form-label"><?= lang('Config.language') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-translate"></i></span>
|
||||||
|
<select class="form-select" name="language" id="language">
|
||||||
|
<?php foreach (get_languages() as $value => $label): ?>
|
||||||
|
<option value="<?= esc($value) ?>" <?= $value === current_language_code(true) . ':' . current_language(true) ? 'selected' : '' ?>><?= esc($label) ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="rtl_language" name="rtl_language" value="rtl_language" <?= $config['rtl_language'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="rtl_language">RTL Language <?= $beta; ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="timezone" class="form-label"><?= lang('Config.timezone') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-clock"></i></span>
|
||||||
|
<?= form_dropdown(
|
||||||
|
'timezone',
|
||||||
|
get_timezones(),
|
||||||
|
$config['timezone'] ? $config['timezone'] : date_default_timezone_get(),
|
||||||
|
['class' => 'form-select']
|
||||||
|
) ?>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="datetimeformat" class="form-label"><?= lang('Config.datetimeformat') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-calendar2"></i></span>
|
||||||
|
<?= form_dropdown(
|
||||||
|
'dateformat',
|
||||||
|
get_dateformats(),
|
||||||
|
$config['dateformat'],
|
||||||
|
['class' => 'form-select']
|
||||||
|
) ?>
|
||||||
|
<?= form_dropdown(
|
||||||
|
'timeformat',
|
||||||
|
get_timeformats(),
|
||||||
|
$config['timeformat'],
|
||||||
|
['class' => 'form-select']
|
||||||
|
) ?>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="date_or_time_format" name="date_or_time_format" value="date_or_time_format" <?= $config['date_or_time_format'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="date_or_time_format"><?= lang('Config.date_or_time_format'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="financial_year" class="form-label"><?= lang('Config.financial_year') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-calendar2-month"></i></span>
|
||||||
|
<select class="form-select" name="financial_year" id="financial_year">
|
||||||
|
<option value="1" <?= ($config['financial_year'] == '1' ? 'selected' : ''); ?>><?= lang('Config.financial_year_jan'); ?></option>
|
||||||
|
<option value="2" <?= ($config['financial_year'] == '2' ? 'selected' : ''); ?>><?= lang('Config.financial_year_feb'); ?></option>
|
||||||
|
<option value="3" <?= ($config['financial_year'] == '3' ? 'selected' : ''); ?>><?= lang('Config.financial_year_mar'); ?></option>
|
||||||
|
<option value="4" <?= ($config['financial_year'] == '4' ? 'selected' : ''); ?>><?= lang('Config.financial_year_apr'); ?></option>
|
||||||
|
<option value="5" <?= ($config['financial_year'] == '5' ? 'selected' : ''); ?>><?= lang('Config.financial_year_may'); ?></option>
|
||||||
|
<option value="6" <?= ($config['financial_year'] == '6' ? 'selected' : ''); ?>><?= lang('Config.financial_year_jun'); ?></option>
|
||||||
|
<option value="7" <?= ($config['financial_year'] == '7' ? 'selected' : ''); ?>><?= lang('Config.financial_year_jul'); ?></option>
|
||||||
|
<option value="8" <?= ($config['financial_year'] == '8' ? 'selected' : ''); ?>><?= lang('Config.financial_year_aug'); ?></option>
|
||||||
|
<option value="9" <?= ($config['financial_year'] == '9' ? 'selected' : ''); ?>><?= lang('Config.financial_year_sep'); ?></option>
|
||||||
|
<option value="10" <?= ($config['financial_year'] == '10' ? 'selected' : ''); ?>><?= lang('Config.financial_year_oct'); ?></option>
|
||||||
|
<option value="11" <?= ($config['financial_year'] == '11' ? 'selected' : ''); ?>><?= lang('Config.financial_year_nov'); ?></option>
|
||||||
|
<option value="12" <?= ($config['financial_year'] == '12' ? 'selected' : ''); ?>><?= lang('Config.financial_year_dec'); ?></option>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_locale"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -354,7 +314,7 @@
|
|||||||
}
|
}
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: '#locale_error_message_box'
|
errorLabelContainer: '.locale_error_message_box'
|
||||||
}));
|
}));
|
||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|||||||
@@ -1,79 +1,66 @@
|
|||||||
|
<?php
|
||||||
|
$tabs = [
|
||||||
|
['id' => 'info', 'icon' => 'bi-shop', 'label' => lang('Config.info'), 'title' => lang('Config.info_configuration')],
|
||||||
|
['id' => 'general', 'icon' => 'bi-sliders', 'label' => lang('Config.general'), 'title' => lang('Config.general_configuration')],
|
||||||
|
['id' => 'appearance', 'icon' => 'bi-eye', 'label' => 'Appearance', 'title' => 'Appearance Configuration'],
|
||||||
|
['id' => 'locale', 'icon' => 'bi-translate', 'label' => lang('Config.locale'), 'title' => lang('Config.locale_configuration')],
|
||||||
|
['id' => 'tax', 'icon' => 'bi-piggy-bank', 'label' => lang('Config.tax'), 'title' => lang('Config.tax_configuration')],
|
||||||
|
['id' => 'barcode', 'icon' => 'bi-upc-scan', 'label' => lang('Config.barcode'), 'title' => lang('Config.barcode_configuration')],
|
||||||
|
['id' => 'stock', 'icon' => 'bi-truck', 'label' => lang('Config.location'), 'title' => lang('Config.location_configuration')],
|
||||||
|
['id' => 'receipt', 'icon' => 'bi-receipt', 'label' => lang('Config.receipt'), 'title' => lang('Config.receipt_configuration')],
|
||||||
|
['id' => 'invoice', 'icon' => 'bi-file-text', 'label' => lang('Config.invoice'), 'title' => lang('Config.invoice_configuration')],
|
||||||
|
['id' => 'shortcuts', 'icon' => 'bi-shift', 'label' => lang('Config.shortcuts'), 'title' => lang('Config.shortcuts_configuration')],
|
||||||
|
['id' => 'reward', 'icon' => 'bi-trophy', 'label' => lang('Config.reward'), 'title' => lang('Config.reward_configuration')],
|
||||||
|
['id' => 'table', 'icon' => 'bi-cup-straw', 'label' => lang('Config.table'), 'title' => lang('Config.table_configuration')],
|
||||||
|
['id' => 'email', 'icon' => 'bi-envelope', 'label' => lang('Config.email'), 'title' => lang('Config.email_configuration')],
|
||||||
|
['id' => 'message', 'icon' => 'bi-chat', 'label' => lang('Config.message'), 'title' => lang('Config.message_configuration')],
|
||||||
|
['id' => 'integrations', 'icon' => 'bi-gear-wide-connected', 'label' => lang('Config.integrations'), 'title' => lang('Config.integrations_configuration')],
|
||||||
|
['id' => 'system', 'icon' => 'bi-info-circle', 'label' => lang('Config.system_info'), 'title' => lang('Config.system_info'), 'view' => 'configs/system_info'],
|
||||||
|
['id' => 'license', 'icon' => 'bi-journal-check', 'label' => lang('Config.license'), 'title' => lang('Config.license_configuration')],
|
||||||
|
];
|
||||||
|
?>
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript" src="resources/clipboard/clipboard.min.js"></script>
|
||||||
dialog_support.init("a.modal-dlg");
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<ul class="nav nav-tabs" data-tabs="tabs">
|
<div class="row">
|
||||||
<li class="active" role="presentation">
|
<div class="col-lg-3 <?= $config['config_menu_position'] == 'start' ? '' : 'order-lg-2' ?>">
|
||||||
<a data-toggle="tab" href="#info_tab" title="<?= lang('Config.info_configuration') ?>"><?= lang('Config.info') ?></a>
|
<div class="list-group d-none d-lg-block" role="tablist">
|
||||||
</li>
|
<?php foreach ($tabs as $i => $tab): ?>
|
||||||
<li role="presentation">
|
<button type="button" class="list-group-item list-group-item-action text-truncate <?= $i === 0 ? 'active' : '' ?>" id="<?= $tab['id'] ?>-tab" data-bs-toggle="tab" data-bs-target="#<?= $tab['id'] ?>" role="tab" title="<?= $tab['title'] ?>">
|
||||||
<a data-toggle="tab" href="#general_tab" title="<?= lang('Config.general_configuration') ?>"><?= lang('Config.general') ?></a>
|
<i class="bi <?= $tab['icon'] ?> me-2"></i><?= $tab['label'] ?>
|
||||||
</li>
|
</button>
|
||||||
<li role="presentation">
|
<?php endforeach ?>
|
||||||
<a data-toggle="tab" href="#tax_tab" title="<?= lang('Config.tax_configuration') ?>"><?= lang('Config.tax') ?></a>
|
</div>
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#locale_tab" title="<?= lang('Config.locale_configuration') ?>"><?= lang('Config.locale') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#barcode_tab" title="<?= lang('Config.barcode_configuration') ?>"><?= lang('Config.barcode') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#stock_tab" title="<?= lang('Config.location_configuration') ?>"><?= lang('Config.location') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#receipt_tab" title="<?= lang('Config.receipt_configuration') ?>"><?= lang('Config.receipt') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#invoice_tab" title="<?= lang('Config.invoice_configuration') ?>"><?= lang('Config.invoice') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#reward_tab" title="<?= lang('Config.reward_configuration') ?>"><?= lang('Config.reward') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#table_tab" title="<?= lang('Config.table_configuration') ?>"><?= lang('Config.table') ?></a>
|
|
||||||
</li>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#system_tab" title="<?= lang('Config.system_conf') ?>"><?= lang('Config.system_conf') ?></a>
|
|
||||||
</li>
|
|
||||||
</ul>
|
|
||||||
|
|
||||||
<div class="tab-content">
|
<div class="nav dropdown d-lg-none mb-3">
|
||||||
<div class="tab-pane fade in active" id="info_tab">
|
<button type="button" class="btn btn-primary w-100 dropdown-toggle text-truncate" id="configs-dropdown" data-bs-toggle="dropdown" aria-expanded="false">
|
||||||
<?= view('configs/info_config') ?>
|
<?= lang('Config.info') ?>
|
||||||
|
</button>
|
||||||
|
<ul class="dropdown-menu w-100" aria-labelledby="configs-dropdown">
|
||||||
|
<?php foreach ($tabs as $i => $tab): ?>
|
||||||
|
<li>
|
||||||
|
<a class="dropdown-item py-2 text-truncate <?= $i === 0 ? 'active' : '' ?>" data-bs-toggle="tab" data-bs-target="#<?= $tab['id'] ?>" role="tab" title="<?= $tab['title'] ?>">
|
||||||
|
<i class="bi <?= $tab['icon'] ?> me-2"></i><?= $tab['label'] ?>
|
||||||
|
</a>
|
||||||
|
</li>
|
||||||
|
<?php endforeach ?>
|
||||||
|
</ul>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="tab-pane" id="general_tab">
|
|
||||||
<?= view('configs/general_config') ?>
|
<div class="col-lg-9 order-lg-1">
|
||||||
</div>
|
<div class="tab-content">
|
||||||
<div class="tab-pane" id="tax_tab">
|
<?php foreach ($tabs as $i => $tab): ?>
|
||||||
<?= view('configs/tax_config') ?>
|
<div class="tab-pane <?= $i === 0 ? 'active' : '' ?>" id="<?= $tab['id'] ?>" role="tabpanel" aria-labelledby="<?= $tab['id'] ?>-tab">
|
||||||
</div>
|
<?= view($tab['view'] ?? 'configs/' . $tab['id'] . '_config') ?>
|
||||||
<div class="tab-pane" id="locale_tab">
|
</div>
|
||||||
<?= view('configs/locale_config') ?>
|
<?php endforeach ?>
|
||||||
</div>
|
</div>
|
||||||
<div class="tab-pane" id="barcode_tab">
|
|
||||||
<?= view('configs/barcode_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="stock_tab">
|
|
||||||
<?= view('configs/stock_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="receipt_tab">
|
|
||||||
<?= view('configs/receipt_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="invoice_tab">
|
|
||||||
<?= view('configs/invoice_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="reward_tab">
|
|
||||||
<?= view('configs/reward_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="table_tab">
|
|
||||||
<?= view('configs/table_config') ?>
|
|
||||||
</div>
|
|
||||||
<div class="tab-pane" id="system_tab">
|
|
||||||
<?= view('configs/system_config') ?>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<script type="text/javascript" src="js/bs-tab_anchor_linking.js"></script>
|
||||||
|
<script type="text/javascript" src="js/bs-validation.js"></script>
|
||||||
|
|
||||||
<?= view('partial/footer') ?>
|
<?= view('partial/footer') ?>
|
||||||
|
|||||||
@@ -4,86 +4,51 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveMessage/', ['id' => 'message_config_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveMessage/', ['id' => 'message_config_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="message_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.message_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="message_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.msg_uid'), 'msg_uid', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-4">
|
<div class="row">
|
||||||
<div class="input-group">
|
<div class="col-12 col-lg-6 mb-3">
|
||||||
<span class="input-group-addon input-sm">
|
<label for="msg_uid" class="form-label"><?= lang('Config.msg_uid'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<span class="glyphicon glyphicon-user"></span>
|
<div class="input-group">
|
||||||
</span>
|
<span class="input-group-text" id="msg_uid-icon"><i class="bi bi-person"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="msg_uid" id="msg_uid" aria-describedby="msg_uid-icon" required value="<?= $config['msg_uid']; ?>">
|
||||||
'name' => 'msg_uid',
|
|
||||||
'id' => 'msg_uid',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['msg_uid']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6 mb-3">
|
||||||
<?= form_label(lang('Config.msg_pwd'), 'msg_pwd', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="msg_pwd" class="form-label"><?= lang('Config.msg_pwd'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group">
|
||||||
<div class="input-group">
|
<span class="input-group-text" id="msg_pwd-icon"><i class="bi bi-lock"></i></span>
|
||||||
<span class="input-group-addon input-sm">
|
<input type="password" class="form-control" name="msg_pwd" id="msg_pwd" aria-describedby="msg_pwd-icon" required value="<?= $config['msg_pwd']; ?>">
|
||||||
<span class="glyphicon glyphicon-lock"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_password([
|
|
||||||
'name' => 'msg_pwd',
|
|
||||||
'id' => 'msg_pwd',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['msg_pwd']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-12 col-lg-6 mb-3">
|
||||||
<?= form_label(lang('Config.msg_src'), 'msg_src', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="msg_src" class="form-label"><?= lang('Config.msg_src'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group">
|
||||||
<div class="input-group">
|
<span class="input-group-text" id="msg_src-icon"><i class="bi bi-megaphone"></i></span>
|
||||||
<span class="input-group-addon input-sm">
|
<input type="text" class="form-control" name="msg_src" id="msg_src" aria-describedby="msg_src-icon" required value="<?= $config['msg_src'] == null ? $config['company'] : $config['msg_src']; ?>">
|
||||||
<span class="glyphicon glyphicon-bullhorn"></span>
|
|
||||||
</span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'msg_src',
|
|
||||||
'id' => 'msg_src',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['msg_src'] == null ? $config['company'] : $config['msg_src']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.msg_msg'), 'msg_msg', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'msg_msg',
|
|
||||||
'id' => 'msg_msg',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['msg_msg'],
|
|
||||||
'placeholder' => lang('Config.msg_msg_placeholder')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_message',
|
|
||||||
'id' => 'submit_message',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<label for="msg_msg" class="form-label"><?= lang('Config.msg_msg'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-chat-quote"></i></span>
|
||||||
|
<textarea class="form-control" name="msg_msg" id="msg_msg" rows="10" placeholder="<?= lang('Config.msg_msg_placeholder'); ?>"><?= esc($config['msg_msg']); ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_message"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -91,7 +56,7 @@
|
|||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
$('#message_config_form').validate($.extend(form_support.handler, {
|
$('#message_config_form').validate($.extend(form_support.handler, {
|
||||||
|
|
||||||
errorLabelContainer: "#message_error_message_box",
|
errorLabelContainer: ".message_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
msg_uid: "required",
|
msg_uid: "required",
|
||||||
|
|||||||
@@ -4,334 +4,199 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveReceipt/', ['id' => 'receipt_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveReceipt/', ['id' => 'receipt_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="receipt_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.receipt_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="receipt_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.receipt_template'), 'receipt_template', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
<div class="row">
|
||||||
<?= form_dropdown(
|
<div class="col-12 col-lg-6">
|
||||||
'receipt_template',
|
<label for="receipt_template" class="form-label"><?= lang('Config.receipt_template'); ?></label>
|
||||||
[
|
<div class="input-group mb-3">
|
||||||
'receipt_default' => lang('Config.receipt_default'),
|
<span class="input-group-text"><i class="bi bi-file-code"></i></span>
|
||||||
'receipt_short' => lang('Config.receipt_short')
|
<select class="form-select" name="receipt_template">
|
||||||
],
|
<option value="receipt_default" <?= $config['receipt_template'] == 'receipt_default' ? 'selected' : '' ?>><?= lang('Config.receipt_default') ?></option>
|
||||||
$config['receipt_template'],
|
<option value="receipt_short" <?= $config['receipt_template'] == 'receipt_short' ? 'selected' : '' ?>><?= lang('Config.receipt_short') ?></option>
|
||||||
'class="form-control input-sm"'
|
</select>
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-6 col-lg-3">
|
||||||
<?= form_label(lang('Config.receipt_font_size'), 'receipt_font_size', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="receipt_font_size" class="form-label"><?= lang('Config.receipt_font_size'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<div class="input-group">
|
<span class="input-group-text"><i class="bi bi-arrows-angle-expand"></i></span>
|
||||||
<?= form_input([
|
<input type="number" class="form-control" name="receipt_font_size" id="receipt_font_size" value="<?= $config['receipt_font_size']; ?>">
|
||||||
'type' => 'number',
|
<span class="input-group-text">px</span>
|
||||||
'min' => '0',
|
|
||||||
'max' => '20',
|
|
||||||
'name' => 'receipt_font_size',
|
|
||||||
'id' => 'receipt_font_size',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['receipt_font_size']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="col-6 col-lg-3">
|
||||||
<?= form_label(lang('Config.print_delay_autoreturn'), 'print_delay_autoreturn', ['class' => 'control-label col-xs-2 required']) ?>
|
<label for="print_delay_autoreturn" class="form-label"><?= lang('Config.print_delay_autoreturn'); ?></label>
|
||||||
<div class="col-xs-2">
|
<div class="input-group mb-3">
|
||||||
<div class="input-group">
|
<span class="input-group-text"><i class="bi bi-stopwatch"></i></span>
|
||||||
<?= form_input([
|
<input type="number" class="form-control" name="print_delay_autoreturn" id="print_delay_autoreturn" value="<?= $config['print_delay_autoreturn']; ?>">
|
||||||
'type' => 'number',
|
<span class="input-group-text">s</span>
|
||||||
'min' => '0',
|
|
||||||
'max' => '30',
|
|
||||||
'name' => 'print_delay_autoreturn',
|
|
||||||
'id' => 'print_delay_autoreturn',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['print_delay_autoreturn']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">s</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.email_receipt_check_behaviour'), 'email_receipt_check_behaviour', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'email_receipt_check_behaviour',
|
|
||||||
'value' => 'always',
|
|
||||||
'checked' => $config['email_receipt_check_behaviour'] == 'always'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.email_receipt_check_behaviour_always') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'email_receipt_check_behaviour',
|
|
||||||
'value' => 'never',
|
|
||||||
'checked' => $config['email_receipt_check_behaviour'] == 'never'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.email_receipt_check_behaviour_never') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'email_receipt_check_behaviour',
|
|
||||||
'value' => 'last',
|
|
||||||
'checked' => $config['email_receipt_check_behaviour'] == 'last'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.email_receipt_check_behaviour_last') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_receipt_check_behaviour'), 'print_receipt_check_behaviour', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_receipt_check_behaviour',
|
|
||||||
'value' => 'always',
|
|
||||||
'checked' => $config['print_receipt_check_behaviour'] == 'always'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.print_receipt_check_behaviour_always') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_receipt_check_behaviour',
|
|
||||||
'value' => 'never',
|
|
||||||
'checked' => $config['print_receipt_check_behaviour'] == 'never'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.print_receipt_check_behaviour_never') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_receipt_check_behaviour',
|
|
||||||
'value' => 'last',
|
|
||||||
'checked' => $config['print_receipt_check_behaviour'] == 'last'
|
|
||||||
]) ?>
|
|
||||||
<?= lang('Config.print_receipt_check_behaviour_last') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_company_name'), 'receipt_show_company_name', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_company_name',
|
|
||||||
'value' => 'receipt_show_company_name',
|
|
||||||
'id' => 'receipt_show_company_name',
|
|
||||||
'checked' => $config['receipt_show_company_name'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_taxes'), 'receipt_show_taxes', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_taxes',
|
|
||||||
'value' => 'receipt_show_taxes',
|
|
||||||
'id' => 'receipt_show_taxes',
|
|
||||||
'checked' => $config['receipt_show_taxes'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_tax_ind'), 'receipt_show_tax_ind', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_tax_ind',
|
|
||||||
'value' => 'receipt_show_tax_ind',
|
|
||||||
'id' => 'receipt_show_tax_ind',
|
|
||||||
'checked' => $config['receipt_show_tax_ind'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_total_discount'), 'receipt_show_total_discount', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_total_discount',
|
|
||||||
'value' => 'receipt_show_total_discount',
|
|
||||||
'id' => 'receipt_show_total_discount',
|
|
||||||
'checked' => $config['receipt_show_total_discount'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_description'), 'receipt_show_description', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_description',
|
|
||||||
'value' => 'receipt_show_description',
|
|
||||||
'id' => 'receipt_show_description',
|
|
||||||
'checked' => $config['receipt_show_description'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_show_serialnumber'), 'receipt_show_serialnumber', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'receipt_show_serialnumber',
|
|
||||||
'value' => 'receipt_show_serialnumber',
|
|
||||||
'id' => 'receipt_show_serialnumber',
|
|
||||||
'checked' => $config['receipt_show_serialnumber'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_silently'), 'print_silently', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'print_silently',
|
|
||||||
'id' => 'print_silently',
|
|
||||||
'value' => 'print_silently',
|
|
||||||
'checked' => $config['print_silently'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_header'), 'print_header', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'print_header',
|
|
||||||
'id' => 'print_header',
|
|
||||||
'value' => 'print_header',
|
|
||||||
'checked' => $config['print_header'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_footer'), 'print_footer', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'print_footer',
|
|
||||||
'id' => 'print_footer',
|
|
||||||
'value' => 'print_footer',
|
|
||||||
'checked' => $config['print_footer'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.receipt_printer'), 'config_receipt_printer', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown('receipt_printer', [], ' ', 'id="receipt_printer" class="form-control"') ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.invoice_printer'), 'config_invoice_printer', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown('invoice_printer', [], ' ', 'id="invoice_printer" class="form-control"') ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.takings_printer'), 'config_takings_printer', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown('takings_printer', [], ' ', 'id="takings_printer" class="form-control"') ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_top_margin'), 'print_top_margin', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => '0',
|
|
||||||
'max' => '20',
|
|
||||||
'name' => 'print_top_margin',
|
|
||||||
'id' => 'print_top_margin',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['print_top_margin']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_left_margin'), 'print_left_margin', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => '0',
|
|
||||||
'max' => '20',
|
|
||||||
'name' => 'print_left_margin',
|
|
||||||
'id' => 'print_left_margin',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['print_left_margin']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_bottom_margin'), 'print_bottom_margin', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => '0',
|
|
||||||
'max' => '20',
|
|
||||||
'name' => 'print_bottom_margin',
|
|
||||||
'id' => 'print_bottom_margin',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['print_bottom_margin']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.print_right_margin'), 'print_right_margin', ['class' => 'control-label col-xs-2 required']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'type' => 'number',
|
|
||||||
'min' => '0',
|
|
||||||
'max' => '20',
|
|
||||||
'name' => 'print_right_margin',
|
|
||||||
'id' => 'print_right_margin',
|
|
||||||
'class' => 'form-control input-sm required',
|
|
||||||
'value' => $config['print_right_margin']
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">px</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_receipt',
|
|
||||||
'id' => 'submit_receipt',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<label for="email_receipt_check_behaviour" class="form-label"><?= lang('Config.email_receipt_check_behaviour'); ?></label>
|
||||||
|
<div class="row mb-3">
|
||||||
|
<div class="col-12">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="email_receipt_check_behaviour" id="email_receipt_check_behaviour_always" value="always" <?= $config['email_receipt_check_behaviour'] == 'always' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="email_receipt_check_behaviour_always"><?= lang('Config.email_receipt_check_behaviour_always') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="email_receipt_check_behaviour" id="email_receipt_check_behaviour_never" value="never" <?= $config['email_receipt_check_behaviour'] == 'never' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="email_receipt_check_behaviour_never"><?= lang('Config.email_receipt_check_behaviour_never') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="email_receipt_check_behaviour" id="email_receipt_check_behaviour_last" value="last" <?= $config['email_receipt_check_behaviour'] == 'last' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="email_receipt_check_behaviour_last"><?= lang('Config.email_receipt_check_behaviour_last') ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="print_receipt_check_behaviour" class="form-label"><?= lang('Config.print_receipt_check_behaviour'); ?></label>
|
||||||
|
<div class="row mb-3">
|
||||||
|
<div class="col-12">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="print_receipt_check_behaviour" id="print_receipt_check_behaviour_always" value="always" <?= $config['print_receipt_check_behaviour'] == 'always' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_receipt_check_behaviour_always"><?= lang('Config.print_receipt_check_behaviour_always') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="print_receipt_check_behaviour" id="print_receipt_check_behaviour_never" value="never" <?= $config['print_receipt_check_behaviour'] == 'never' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_receipt_check_behaviour_never"><?= lang('Config.print_receipt_check_behaviour_never') ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="print_receipt_check_behaviour" id="print_receipt_check_behaviour_last" value="last" <?= $config['print_receipt_check_behaviour'] == 'last' ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_receipt_check_behaviour_last"><?= lang('Config.print_receipt_check_behaviour_last') ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_company_name" name="receipt_show_company_name" value="receipt_show_company_name" <?= $config['receipt_show_company_name'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_company_name"><?= lang('Config.receipt_show_company_name'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_taxes" name="receipt_show_taxes" value="receipt_show_taxes" <?= $config['receipt_show_taxes'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_taxes"><?= lang('Config.receipt_show_taxes'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_tax_ind" name="receipt_show_tax_ind" value="receipt_show_tax_ind" <?= $config['receipt_show_tax_ind'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_tax_ind"><?= lang('Config.receipt_show_tax_ind'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_total_discount" name="receipt_show_total_discount" value="receipt_show_total_discount" <?= $config['receipt_show_total_discount'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_total_discount"><?= lang('Config.receipt_show_total_discount'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_description" name="receipt_show_description" value="receipt_show_description" <?= $config['receipt_show_description'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_description"><?= lang('Config.receipt_show_description'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="receipt_show_serialnumber" name="receipt_show_serialnumber" value="receipt_show_serialnumber" <?= $config['receipt_show_serialnumber'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="receipt_show_serialnumber"><?= lang('Config.receipt_show_serialnumber'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="print_silently" name="print_silently" value="print_silently" <?= $config['print_silently'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_silently"><?= lang('Config.print_silently'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="print_header" name="print_header" value="print_header" <?= $config['print_header'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_header"><?= lang('Config.print_header'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="print_footer" name="print_footer" value="print_footer" <?= $config['print_footer'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="print_footer"><?= lang('Config.print_footer'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="receipt_printer" class="form-label"><?= lang('Config.receipt_printer'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-printer"></i></span>
|
||||||
|
<select class="form-select" name="receipt_printer" id="receipt_printer"></select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="invoice_printer" class="form-label"><?= lang('Config.invoice_printer'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-printer"></i></span>
|
||||||
|
<select class="form-select" name="invoice_printer" id="invoice_printer"></select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="takings_printer" class="form-label"><?= lang('Config.takings_printer'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-printer"></i></span>
|
||||||
|
<select class="form-select" name="takings_printer" id="takings_printer"></select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="print_top_margin" class="form-label"><?= lang('Config.print_top_margin'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-bar-down"></i></span>
|
||||||
|
<input type="number" class="form-control" name="print_top_margin" id="print_top_margin" value="<?= $config['print_top_margin']; ?>">
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="print_left_margin" class="form-label"><?= lang('Config.print_left_margin'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-bar-right"></i></span>
|
||||||
|
<input type="number" class="form-control" name="print_left_margin" id="print_left_margin" value="<?= $config['print_left_margin']; ?>">
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="print_bottom_margin" class="form-label"><?= lang('Config.print_bottom_margin'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-bar-up"></i></span>
|
||||||
|
<input type="number" class="form-control" name="print_bottom_margin" id="print_bottom_margin" value="<?= $config['print_bottom_margin']; ?>">
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-6 col-lg-3">
|
||||||
|
<label for="print_right_margin" class="form-label"><?= lang('Config.print_right_margin'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-arrow-bar-left"></i></span>
|
||||||
|
<input type="number" class="form-control" name="print_right_margin" id="print_right_margin" value="<?= $config['print_right_margin']; ?>">
|
||||||
|
<span class="input-group-text">px</span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_receipt"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -370,6 +235,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -379,7 +245,7 @@
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: "#receipt_error_message_box",
|
errorLabelContainer: ".receipt_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
print_top_margin: {
|
print_top_margin: {
|
||||||
|
|||||||
@@ -5,38 +5,28 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveRewards/', ['id' => 'reward_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveRewards/', ['id' => 'reward_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="reward_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.reward_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="reward_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.customer_reward_enable'), 'customer_reward_enable', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'customer_reward_enable',
|
|
||||||
'value' => 'customer_reward_enable',
|
|
||||||
'id' => 'customer_reward_enable',
|
|
||||||
'checked' => $config['customer_reward_enable'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div id="customer_rewards">
|
<div class="form-check form-switch mb-3">
|
||||||
<?= view('partial/customer_rewards', ['customer_rewards' => $customer_rewards]) ?>
|
<input class="form-check-input" type="checkbox" role="switch" id="customer_reward_enable" name="customer_reward_enable" value="customer_reward_enable" <?= $config['customer_reward_enable'] == 1 ? 'checked' : '' ?>>
|
||||||
</div>
|
<label class="form-check-label" for="customer_reward_enable"><?= lang('Config.customer_reward_enable'); ?></label>
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_reward',
|
|
||||||
'id' => 'submit_reward',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row" id="customer_rewards">
|
||||||
|
<?= view('partial/customer_rewards', ['customer_rewards' => $customer_rewards]) ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_reward"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -76,9 +66,9 @@
|
|||||||
var new_block = block.insertAfter($(this).parent());
|
var new_block = block.insertAfter($(this).parent());
|
||||||
var new_block_id = 'customer_reward_' + ++id;
|
var new_block_id = 'customer_reward_' + ++id;
|
||||||
var new_block_id_next = 'reward_points_' + id;
|
var new_block_id_next = 'reward_points_' + id;
|
||||||
$(new_block).find('label').html("<?= lang('Config.customer_reward') ?> " + ++table_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2');
|
$(new_block).find('label').html("<?= lang('Config.customer_reward') ?> " + ++table_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2'); // TODO-BS5 change classes from bs3 to bs5
|
||||||
$(new_block).find("input[id='" + previous_id + "']").attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val('');
|
$(new_block).find("input[id='" + previous_id + "']").attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val(''); // TODO-BS5 change classes from bs3 to bs5
|
||||||
$(new_block).find("input[id='" + previous_id_next + "']").attr('id', new_block_id_next).removeAttr('disabled').attr('name', new_block_id_next).attr('class', 'form-control input-sm').val('');
|
$(new_block).find("input[id='" + previous_id_next + "']").attr('id', new_block_id_next).removeAttr('disabled').attr('name', new_block_id_next).attr('class', 'form-control input-sm').val(''); // TODO-BS5 change classes from bs3 to bs5
|
||||||
hide_show_remove();
|
hide_show_remove();
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -119,6 +109,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -129,7 +120,7 @@
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: "#reward_error_message_box",
|
errorLabelContainer: ".reward_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
<?php
|
<?php
|
||||||
|
|||||||
79
app/Views/configs/shortcuts_config.php
Normal file
79
app/Views/configs/shortcuts_config.php
Normal file
@@ -0,0 +1,79 @@
|
|||||||
|
<?php
|
||||||
|
/**
|
||||||
|
* @var array $config
|
||||||
|
* @var array $keyboardShortcutOptions
|
||||||
|
* @var array $keyboardShortcuts
|
||||||
|
*/
|
||||||
|
|
||||||
|
$keyboardShortcuts ??= [];
|
||||||
|
$keyboardShortcutOptions ??= [];
|
||||||
|
$config ??= [];
|
||||||
|
|
||||||
|
$shortcutLabels = [
|
||||||
|
'cancel' => lang('Sales.key_cancel'),
|
||||||
|
'items' => lang('Sales.key_item_search'),
|
||||||
|
'customers' => lang('Sales.key_customer_search'),
|
||||||
|
'suspend' => lang('Sales.key_suspend'),
|
||||||
|
'suspended' => lang('Sales.key_suspended'),
|
||||||
|
'amount' => lang('Sales.key_tendered'),
|
||||||
|
'payment' => lang('Sales.key_payment'),
|
||||||
|
'complete' => lang('Sales.key_finish_sale'),
|
||||||
|
'finish' => lang('Sales.key_finish_quote'),
|
||||||
|
'help' => lang('Sales.key_help_modal')
|
||||||
|
];
|
||||||
|
?>
|
||||||
|
|
||||||
|
<?= form_open('config/saveShortcuts', ['id' => 'shortcuts_config_form']) ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = lang('Config.shortcuts_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
|
<ul id="error_message_box" class="shortcuts_error_message_box alert alert-warning d-none"></ul>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<?php foreach ($shortcutLabels as $name => $label): ?>
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<?= form_label($label, 'key_' . $name, ['class' => 'form-label']) ?>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-keyboard"></i></span>
|
||||||
|
<?php $keyboardShortcutSelectedValue = $keyboardShortcuts[$name]['value'] ?? ''; ?>
|
||||||
|
<?= form_dropdown('key_' . $name, $keyboardShortcutOptions, $keyboardShortcutSelectedValue, 'class="form-select"') ?>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_shortcuts"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<?= form_close() ?>
|
||||||
|
|
||||||
|
<script type="text/javascript">
|
||||||
|
$('#shortcuts_config_form').validate($.extend(form_support.handler, {
|
||||||
|
submitHandler: function(form) {
|
||||||
|
$(form).ajaxSubmit({
|
||||||
|
success: function(response) {
|
||||||
|
$.notify({
|
||||||
|
message: response.message
|
||||||
|
}, {
|
||||||
|
type: response.success ? 'success' : 'danger'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
error: function(xhr) {
|
||||||
|
const rawMessage = xhr.responseJSON?.message ?? xhr.responseText ?? <?= json_encode(lang('Config.shortcuts_save_error')) ?>;
|
||||||
|
$.notify({
|
||||||
|
message: DOMPurify.sanitize(rawMessage)
|
||||||
|
}, {
|
||||||
|
type: 'danger'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
dataType: 'json'
|
||||||
|
});
|
||||||
|
},
|
||||||
|
|
||||||
|
errorLabelContainer: '.shortcuts_error_message_box'
|
||||||
|
}));
|
||||||
|
</script>
|
||||||
@@ -4,26 +4,23 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveLocations/', ['id' => 'location_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveLocations/', ['id' => 'location_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="stock_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.location_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div id="stock_locations">
|
<ul id="error_message_box" class="stock_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= view('partial/stock_locations', ['stock_locations' => $stock_locations]) ?>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
<div id="stock_locations">
|
||||||
'name' => 'submit_stock',
|
<?= view('partial/stock_locations', ['stock_locations' => $stock_locations]) ?>
|
||||||
'id' => 'submit_stock',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_stock"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -43,8 +40,8 @@
|
|||||||
var block = $(this).parent().clone(true);
|
var block = $(this).parent().clone(true);
|
||||||
var new_block = block.insertAfter($(this).parent());
|
var new_block = block.insertAfter($(this).parent());
|
||||||
var new_block_id = 'stock_location[]';
|
var new_block_id = 'stock_location[]';
|
||||||
$(new_block).find('label').html("<?= lang('Config.stock_location') ?> " + ++location_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2');
|
$(new_block).find('label').html("<?= lang('Config.stock_location') ?> " + ++location_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2'); // TODO-BS5 change classes from bs3 to bs5
|
||||||
$(new_block).find('input').attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val('');
|
$(new_block).find('input').attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val(''); // TODO-BS5 change classes from bs3 to bs5
|
||||||
hide_show_remove();
|
hide_show_remove();
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -79,6 +76,7 @@
|
|||||||
$(form).ajaxSubmit({
|
$(form).ajaxSubmit({
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
@@ -89,7 +87,7 @@
|
|||||||
});
|
});
|
||||||
},
|
},
|
||||||
|
|
||||||
errorLabelContainer: "#stock_error_message_box",
|
errorLabelContainer: ".stock_error_message_box",
|
||||||
|
|
||||||
rules: {
|
rules: {
|
||||||
<?php
|
<?php
|
||||||
|
|||||||
@@ -1,17 +0,0 @@
|
|||||||
<br>
|
|
||||||
<div class="container-fluid">
|
|
||||||
<ul class="nav nav-tabs" id="myTabs" data-toggle="tab">
|
|
||||||
<li class="active"><a href="#system_tabs" data-toggle="tab" title="<?= lang('Config.system_conf') ?>"><?= lang('Config.system_conf') ?></a></li>
|
|
||||||
<li><a href="#email_tabs" data-toggle="tab" title="<?= lang('Config.email_configuration') ?>"><?= lang('Config.email') ?></a></li>
|
|
||||||
<li><a href="#message_tabs" data-toggle="tab" title="<?= lang('Config.message_configuration') ?>"><?= lang('Config.message') ?></a></li>
|
|
||||||
<li><a href="#integrations_tabs" data-toggle="tab" title="<?= lang('Config.integrations_configuration') ?>"><?= lang('Config.integrations') ?></a></li>
|
|
||||||
<li><a href="#license_tabs" data-toggle="tab" title="<?= lang('Config.license_configuration') ?>"><?= lang('Config.license') ?></a></li>
|
|
||||||
</ul>
|
|
||||||
<div class="tab-content">
|
|
||||||
<div class="tab-pane active" id="system_tabs"><?= view('configs/system_info') ?></div>
|
|
||||||
<div class="tab-pane" id="email_tabs"><?= view('configs/email_config') ?></div>
|
|
||||||
<div class="tab-pane" id="message_tabs"><?= view('configs/message_config') ?></div>
|
|
||||||
<div class="tab-pane" id="integrations_tabs"><?= view('configs/integrations_config') ?></div>
|
|
||||||
<div class="tab-pane" id="license_tabs"><br><?= view('configs/license_config') ?></div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
@@ -6,48 +6,97 @@
|
|||||||
|
|
||||||
use Config\OSPOS;
|
use Config\OSPOS;
|
||||||
|
|
||||||
|
|
||||||
|
$logs = WRITEPATH . 'logs/';
|
||||||
|
$uploads = FCPATH . 'uploads/';
|
||||||
|
$images = FCPATH . 'uploads/item_pics/';
|
||||||
|
$importCustomers = WRITEPATH . '/uploads/importCustomers.csv'; //TODO: This variable does not follow naming conventions for the project.
|
||||||
|
$bullet = '»' . ' ';
|
||||||
|
$divider = ' ·' . ' ';
|
||||||
|
$enabled = '<span class="text-success">✓ Enabled</span>';
|
||||||
|
$disabled = '<span class="text-danger">✗ Disabled</span>';
|
||||||
|
$writable = '<span class="text-success">✓ Writable</span>';
|
||||||
|
$notwritable = '<span class="text-danger">✗ Not Writable</span>';
|
||||||
|
$readable = '<span class="text-success">✓ Readable</span>';
|
||||||
|
$notreadable = '<span class="text-danger">✗ Not Readable</span>';
|
||||||
|
$permissions_check = '<span class="text-success">✓ Security Check Passed</span>';
|
||||||
|
$permissions_fail = '<span class="text-danger">✗ Vulnerable or Incorrect Permissions</span>';
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<style>
|
<?php
|
||||||
a:hover {
|
$title_info['config_title'] = lang('Config.system_info');
|
||||||
cursor: pointer;
|
echo view('configs/config_header', $title_info);
|
||||||
}
|
?>
|
||||||
|
|
||||||
hidden {
|
<div class="mb-3"><?= lang('Config.server_notice'); ?></div>
|
||||||
visibility: hidden;
|
|
||||||
}
|
|
||||||
</style>
|
|
||||||
|
|
||||||
<script type="text/javascript" src="js/clipboard.min.js"></script>
|
<form id="copy-issue">
|
||||||
|
|
||||||
<div id="config_wrapper" class="col-sm-12">
|
<?php
|
||||||
<?= lang('Config.server_notice') ?>
|
if (!((substr(decoct(fileperms($logs)), -4) == 750)
|
||||||
<div class="container">
|
&& (substr(decoct(fileperms($uploads)), -4) == 750)
|
||||||
<div class="row">
|
&& (substr(decoct(fileperms($images)), -4) == 750)
|
||||||
<div class="col-sm-2" style="text-align: left;"><br>
|
&& ((substr(decoct(fileperms($importCustomers)), -4) == 640)
|
||||||
<p style="min-height: 14.7em; font-weight: bold;">General Info</p>
|
|| (substr(decoct(fileperms($importCustomers)), -4) == 660)))) {
|
||||||
<p style="min-height: 10.5em; font-weight: bold;">User Setup</p><br>
|
echo '<div class="card border-danger-subtle mb-4">
|
||||||
<p style="font-weight: bold;">Permissions</p>
|
<div class="card-header bg-danger-subtle border-danger-subtle fw-bold"><i class="bi bi-exclamation-circle"></i> ' . lang('Config.security_issue') . '</div>
|
||||||
|
<div class="card-body">
|
||||||
|
<p class="card-text">' . lang('Config.perm_risk') . '</p>
|
||||||
|
<ul class="list-unstyled mb-0">';
|
||||||
|
}
|
||||||
|
if (substr(decoct(fileperms($logs)), -4) != 750) {
|
||||||
|
echo '<li class="card-text">' . $bullet . '<code>writable/logs</code> ' . lang('Config.is_writable') . '</li>';
|
||||||
|
}
|
||||||
|
|
||||||
|
if (substr(decoct(fileperms($uploads)), -4) != 750) {
|
||||||
|
echo '<li class="card-text">' . $bullet . '<code>public/uploads</code> ' . lang('Config.is_writable') . '</li>';
|
||||||
|
}
|
||||||
|
|
||||||
|
if (substr(decoct(fileperms($images)), -4) != 750) {
|
||||||
|
echo '<li class="card-text">' . $bullet . '<code>public/uploads/item_pics</code> ' . lang('Config.is_writable') . '</li>';
|
||||||
|
}
|
||||||
|
|
||||||
|
if (!((substr(decoct(fileperms($importCustomers)), -4) == 640)
|
||||||
|
|| (substr(decoct(fileperms($importCustomers)), -4) == 660))) {
|
||||||
|
echo '<li class="card-text">' . $bullet . '<code>importCustomers.csv</code> ' . lang('Config.is_readable') . '</li>';
|
||||||
|
}
|
||||||
|
echo '</div></div>';
|
||||||
|
?>
|
||||||
|
|
||||||
|
<div class="row mb-3">
|
||||||
|
<label for="general-info" class="col-12 col-lg-2 form-label fw-bold">General Info</label>
|
||||||
|
<div class="col-12 col-lg-10" id="general-info">
|
||||||
|
<?= lang('Config.ospos_info') . ': ' . esc(config('App')->application_version) . ' - ' . esc(substr(config(OSPOS::class)->commit_sha1, 0, 6)); ?><br>
|
||||||
|
<div>Language Code: <?= current_language_code(); ?></div><br>
|
||||||
|
<div id="time-error" class="row mb-3 d-none">
|
||||||
|
<div class="col-12 text-danger"><?= lang('Config.timezone_error'); ?></div>
|
||||||
|
<div class="col-6">
|
||||||
|
<label for="timezone"><?= lang('Config.user_timezone'); ?></label>
|
||||||
|
<div id="timezone"></div>
|
||||||
|
</div>
|
||||||
|
<div class="col-6">
|
||||||
|
<label for="ostimezone"><?= lang('Config.os_timezone'); ?></label>
|
||||||
|
<div id="ostimezone"><?= $config['timezone']; ?></div>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
<div class="col-sm-8" id="issuetemplate" style="text-align: left;"><br>
|
<span>Extensions & Modules:</span><br>
|
||||||
<?= lang('Config.ospos_info') . ':' ?>
|
<ul class="list-unstyled">
|
||||||
<?= esc(config('App')->application_version) ?> - <?= esc(substr(config(OSPOS::class)->commit_sha1, 0, 6)) ?><br>
|
<li><?= $bullet . 'GD: ', extension_loaded('gd') ? $enabled : $disabled; ?></li>
|
||||||
Language Code: <?= current_language_code() ?><br><br>
|
<li><?= $bullet . 'BC Math: ', extension_loaded('bcmath') ? $enabled : $disabled; ?></li>
|
||||||
<div id="TimeError"></div>
|
<li><?= $bullet . 'INTL: ', extension_loaded('intl') ? $enabled : $disabled; ?></li>
|
||||||
Extensions & Modules:<br>
|
<li><?= $bullet . 'OpenSSL: ', extension_loaded('openssl') ? $enabled : $disabled; ?></li>
|
||||||
<?php
|
<li><?= $bullet . 'MBString: ', extension_loaded('mbstring') ? $enabled : $disabled; ?></li>
|
||||||
echo "» GD: ", extension_loaded('gd') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
<li><?= $bullet . 'Curl: ', extension_loaded('curl') ? $enabled : $disabled; ?></li>
|
||||||
echo "» BC Math: ", extension_loaded('bcmath') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
<li><?= $bullet . 'Xml: ', extension_loaded('xml') ? $enabled : $disabled; ?></li>
|
||||||
echo "» INTL: ", extension_loaded('intl') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
</ul>
|
||||||
echo "» OpenSSL: ", extension_loaded('openssl') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
</div>
|
||||||
echo "» MBString: ", extension_loaded('mbstring') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
</div>
|
||||||
echo "» Curl: ", extension_loaded('curl') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br>';
|
|
||||||
echo "» Json: ", extension_loaded('json') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br><br>';
|
<div class="row mb-3">
|
||||||
echo "» Xml: ", extension_loaded('xml') ? '<span style="color: green;">Enabled ✓</span>' : '<span style="color: red;">Disabled ✗</span>', '<br><br>';
|
<label for="user-setup" class="col-12 col-lg-2 form-label fw-bold">User Setup</label>
|
||||||
?>
|
<div class="col-12 col-lg-10" id="user-setup">
|
||||||
User Configuration:<br>
|
<ul class="list-unstyled">
|
||||||
.Browser:
|
<?php
|
||||||
<?php
|
|
||||||
/**
|
/**
|
||||||
* @param string $userAgent
|
* @param string $userAgent
|
||||||
* @return string
|
* @return string
|
||||||
@@ -55,162 +104,169 @@ use Config\OSPOS;
|
|||||||
function getBrowserNameAndVersion(string $userAgent): string
|
function getBrowserNameAndVersion(string $userAgent): string
|
||||||
{
|
{
|
||||||
$browser = match (true) {
|
$browser = match (true) {
|
||||||
strpos($userAgent, 'Opera') !== false || strpos($userAgent, 'OPR/') !== false => 'Opera',
|
strpos($userAgent, 'Opera') !== false || strpos($userAgent, 'OPR/') !== false => 'Opera',
|
||||||
strpos($userAgent, 'Edge') !== false => 'Edge',
|
strpos($userAgent, 'Edge') !== false => 'Edge',
|
||||||
strpos($userAgent, 'Chrome') !== false => 'Chrome',
|
strpos($userAgent, 'Chrome') !== false => 'Chrome',
|
||||||
strpos($userAgent, 'Safari') !== false => 'Safari',
|
strpos($userAgent, 'Safari') !== false => 'Safari',
|
||||||
strpos($userAgent, 'Firefox') !== false => 'Firefox',
|
strpos($userAgent, 'Firefox') !== false => 'Firefox',
|
||||||
strpos($userAgent, 'MSIE') !== false || strpos($userAgent, 'Trident/7') !== false => 'Internet Explorer',
|
strpos($userAgent, 'MSIE') !== false || strpos($userAgent, 'Trident/7') !== false => 'Internet Explorer',
|
||||||
default => 'Other',
|
default => 'Other',
|
||||||
};
|
};
|
||||||
|
|
||||||
$version = match ($browser) {
|
$version = match ($browser) {
|
||||||
'Opera' => preg_match('/(Opera|OPR)\/([0-9.]+)/', $userAgent, $matches) ? $matches[2] : '',
|
'Opera' => preg_match('/(Opera|OPR)\/([0-9.]+)/', $userAgent, $matches) ? $matches[2] : '',
|
||||||
'Edge' => preg_match('/Edge\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
'Edge' => preg_match('/Edge\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
||||||
'Chrome' => preg_match('/Chrome\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
'Chrome' => preg_match('/Chrome\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
||||||
'Safari' => preg_match('/Version\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
'Safari' => preg_match('/Version\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
||||||
'Firefox' => preg_match('/Firefox\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
'Firefox' => preg_match('/Firefox\/([0-9.]+)/', $userAgent, $matches) ? $matches[1] : '',
|
||||||
'Internet Explorer' => preg_match('/(MSIE|rv:)([0-9.]+)/', $userAgent, $matches) ? $matches[2] : '',
|
'Internet Explorer' => preg_match('/(MSIE|rv:)([0-9.]+)/', $userAgent, $matches) ? $matches[2] : '',
|
||||||
default => '',
|
default => '',
|
||||||
};
|
};
|
||||||
|
|
||||||
return $browser . ($version ? ' ' . $version : '');
|
return $browser . ($version ? ' ' . $version : '');
|
||||||
}
|
}
|
||||||
echo esc(getBrowserNameAndVersion($_SERVER['HTTP_USER_AGENT']));
|
?>
|
||||||
?><br>
|
<li><?= $bullet . 'Browser: ' . esc(getBrowserNameAndVersion($_SERVER['HTTP_USER_AGENT'])); ?></li>
|
||||||
Server Software: <?= esc($_SERVER['SERVER_SOFTWARE']) ?><br>
|
<li><?= $bullet . 'Server Software: ' . esc($_SERVER['SERVER_SOFTWARE']); ?></li>
|
||||||
PHP Version: <?= PHP_VERSION ?><br>
|
<li><?= $bullet . 'PHP Version: ' . PHP_VERSION; ?></li>
|
||||||
DB Version: <?= esc($dbVersion) ?><br>
|
<li><?= $bullet . 'DB Version: ' . esc($dbVersion); ?></li>
|
||||||
Server Port: <?= esc($_SERVER['SERVER_PORT']) ?><br>
|
<li><?= $bullet . 'Server Port: ' . esc($_SERVER['SERVER_PORT']); ?></li>
|
||||||
OS: <?= php_uname('s') . ' ' . php_uname('r') ?><br><br>
|
<li><?= $bullet . 'OS: ' . php_uname('s') . ' ' . php_uname('r'); ?></li>
|
||||||
<br><br>
|
</ul>
|
||||||
|
|
||||||
File Permissions:<br>
|
|
||||||
» [writable/logs:]
|
|
||||||
<?php $logs = WRITEPATH . 'logs/';
|
|
||||||
$uploads = FCPATH. 'uploads/';
|
|
||||||
$images = FCPATH. 'uploads/item_pics/';
|
|
||||||
$importCustomers = WRITEPATH . '/uploads/importCustomers.csv'; // TODO: This variable does not follow naming conventions for the project.
|
|
||||||
|
|
||||||
if (is_writable($logs)) {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($logs)), -4) . ' | ' . '<span style="color: green;"> Writable ✓ </span>';
|
|
||||||
} else {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($logs)), -4) . ' | ' . '<span style="color: red;"> Not Writable ✗ </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
clearstatcache();
|
|
||||||
if (is_writable($logs) && substr(decoct(fileperms($logs)), -4) != 750) {
|
|
||||||
echo ' | <span style="color: red;">Vulnerable or Incorrect Permissions ✗</span>';
|
|
||||||
} else {
|
|
||||||
echo ' | <span style="color: green;">Security Check Passed ✓</span>';
|
|
||||||
}
|
|
||||||
clearstatcache();
|
|
||||||
?>
|
|
||||||
<br>
|
|
||||||
» [public/uploads:]
|
|
||||||
<?php
|
|
||||||
if (is_writable($uploads)) {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($uploads)), -4) . ' | ' . '<span style="color: green;"> Writable ✓ </span>';
|
|
||||||
} else {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($uploads)), -4) . ' | ' . '<span style="color: red;"> Not Writable ✗ </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
clearstatcache();
|
|
||||||
|
|
||||||
if (is_writable($uploads) && substr(decoct(fileperms($uploads)), -4) != 750) {
|
|
||||||
echo ' | <span style="color: red;">Vulnerable or Incorrect Permissions ✗</span>';
|
|
||||||
} else {
|
|
||||||
echo ' | <span style="color: green;">Security Check Passed ✓ </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
clearstatcache();
|
|
||||||
?>
|
|
||||||
<br>
|
|
||||||
» [public/uploads/item_pics:]
|
|
||||||
<?php
|
|
||||||
if (is_writable($images)) {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($images)), -4) . ' | ' . '<span style="color: green;"> Writable ✓ </span>';
|
|
||||||
} else {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($images)), -4) . ' | ' . '<span style="color: red;"> Not Writable ✗ </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
clearstatcache();
|
|
||||||
|
|
||||||
if (substr(decoct(fileperms($images)), -4) != 750) {
|
|
||||||
echo ' | <span style="color: red;">Vulnerable or Incorrect Permissions ✗</span>';
|
|
||||||
} else {
|
|
||||||
echo ' | <span style="color: green;">Security Check Passed ✓ </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
clearstatcache();
|
|
||||||
?>
|
|
||||||
<br>
|
|
||||||
» [importCustomers.csv:]
|
|
||||||
<?php
|
|
||||||
if (is_readable($importCustomers)) {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($importCustomers)), -4) . ' | ' . '<span style="color: green;"> Readable ✓ </span>';
|
|
||||||
} else {
|
|
||||||
echo ' - ' . substr(sprintf("%o", fileperms($importCustomers)), -4) . ' | ' . '<span style="color: red;"> Not Readable ✗ </span>';
|
|
||||||
}
|
|
||||||
clearstatcache();
|
|
||||||
|
|
||||||
if (!((substr(decoct(fileperms($importCustomers)), -4) == 640) || (substr(decoct(fileperms($importCustomers)), -4) == 660))) {
|
|
||||||
echo ' | <span style="color: red;">Vulnerable or Incorrect Permissions ✗</span>';
|
|
||||||
} else {
|
|
||||||
echo ' | <span style="color: green;">Security Check Passed ✓ </span>';
|
|
||||||
}
|
|
||||||
clearstatcache();
|
|
||||||
?>
|
|
||||||
<br>
|
|
||||||
<?php
|
|
||||||
if (!((substr(decoct(fileperms($logs)), -4) == 750)
|
|
||||||
&& (substr(decoct(fileperms($uploads)), -4) == 750)
|
|
||||||
&& (substr(decoct(fileperms($images)), -4) == 750)
|
|
||||||
&& ((substr(decoct(fileperms($importCustomers)), -4) == 640)
|
|
||||||
|| (substr(decoct(fileperms($importCustomers)), -4) == 660)))) {
|
|
||||||
echo '<br><span style="color: red;"><strong>' . lang('Config.security_issue') . '</strong> <br>' . lang('Config.perm_risk') . '</span><br>';
|
|
||||||
} else {
|
|
||||||
echo '<br><span style="color: green;">' . lang('Config.no_risk') . '</strong> <br> </span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (substr(decoct(fileperms($logs)), -4) != 750) {
|
|
||||||
echo '<br><span style="color: red;"> » [writable/logs:] ' . lang('Config.is_writable') . '</span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (substr(decoct(fileperms($uploads)), -4) != 750) {
|
|
||||||
echo '<br><span style="color: red;"> » [writable/uploads:] ' . lang('Config.is_writable') . '</span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (substr(decoct(fileperms($images)), -4) != 750) {
|
|
||||||
echo '<br><span style="color: red;"> » [writable/uploads/item_pics:] ' . lang('Config.is_writable') . '</span>';
|
|
||||||
}
|
|
||||||
|
|
||||||
if (!((substr(decoct(fileperms($importCustomers)), -4) == 640)
|
|
||||||
|| (substr(decoct(fileperms($importCustomers)), -4) == 660))) {
|
|
||||||
echo '<br><span style="color: red;"> » [importCustomers.csv:] ' . lang('Config.is_readable') . '</span>';
|
|
||||||
}
|
|
||||||
?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row mb-3">
|
||||||
|
<label for="permissions" class="col-12 col-lg-2 form-label fw-bold">Permissions</label>
|
||||||
|
<div class="col-12 col-lg-10" id="permissions">
|
||||||
|
<ul class="list-unstyled">
|
||||||
|
<li>
|
||||||
|
<?= $bullet; ?><code>writable/logs</code>
|
||||||
|
<?php
|
||||||
|
if (is_writable($logs)) {
|
||||||
|
echo substr(sprintf("%o", fileperms($logs)), -4) . $divider . $writable;
|
||||||
|
} else {
|
||||||
|
echo substr(sprintf("%o", fileperms($logs)), -4) . $divider . $notwritable;
|
||||||
|
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
echo $divider;
|
||||||
|
|
||||||
|
if (is_writable($logs) && substr(decoct(fileperms($logs)), -4) != 750) {
|
||||||
|
echo $permissions_fail;
|
||||||
|
} else {
|
||||||
|
echo $permissions_check;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
?>
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<?= $bullet; ?><code>public/uploads</code>
|
||||||
|
<?php
|
||||||
|
if(is_writable($uploads)) {
|
||||||
|
echo substr(sprintf("%o",fileperms($uploads)),-4) . $divider . $writable;
|
||||||
|
} else {
|
||||||
|
echo substr(sprintf("%o",fileperms($uploads)),-4) . $divider . $notwritable;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
echo $divider;
|
||||||
|
|
||||||
|
if(is_writable($uploads) && substr(decoct(fileperms($uploads)), -4) != 750 ) {
|
||||||
|
echo $permissions_fail;
|
||||||
|
} else {
|
||||||
|
echo $permissions_check;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
?>
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<?= $bullet; ?><code>public/uploads/item_pics</code>
|
||||||
|
<?php
|
||||||
|
if (is_writable($images)) {
|
||||||
|
echo substr(sprintf("%o", fileperms($images)), -4) . $divider . $writable;
|
||||||
|
} else {
|
||||||
|
echo substr(sprintf("%o", fileperms($images)), -4) . $divider . $notwritable;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
echo $divider;
|
||||||
|
|
||||||
|
if (substr(decoct(fileperms($images)), -4) != 750) {
|
||||||
|
echo $permissions_fail;
|
||||||
|
} else {
|
||||||
|
echo $permissions_check;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
?>
|
||||||
|
</li>
|
||||||
|
<li>
|
||||||
|
<?= $bullet; ?><code>importCustomers.csv</code>
|
||||||
|
<?php
|
||||||
|
if (is_readable($importCustomers)) {
|
||||||
|
echo substr(sprintf("%o", fileperms($importCustomers)), -4) . $divider . $readable;
|
||||||
|
} else {
|
||||||
|
echo substr(sprintf("%o", fileperms($importCustomers)), -4) . $divider . $notreadable;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
echo $divider;
|
||||||
|
|
||||||
|
if (!((substr(decoct(fileperms($importCustomers)), -4) == 640) || (substr(decoct(fileperms($importCustomers)), -4) == 660))) {
|
||||||
|
echo $permissions_fail;
|
||||||
|
} else {
|
||||||
|
echo $permissions_check;
|
||||||
|
}
|
||||||
|
clearstatcache();
|
||||||
|
|
||||||
|
?>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
<?php
|
||||||
|
if (((substr(decoct(fileperms($logs)), -4) == 750) && (substr(decoct(fileperms($uploads)), -4) == 750) && (substr(decoct(fileperms($images)), -4) == 750) && ((substr(decoct(fileperms($importCustomers)), -4) == 640) || (substr(decoct(fileperms($importCustomers)), -4) == 660)))) {
|
||||||
|
echo '<span class="text-success">' . lang('Config.no_risk') . '</span>';
|
||||||
|
}
|
||||||
|
?>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</form>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-center gap-3">
|
||||||
|
<button type="button" class="copy btn btn-secondary" data-clipboard-target="#copy-issue"><i class="bi bi-clipboard-plus"></i> Copy Info</button> <!-- TODO-BS5 add to translations -->
|
||||||
|
<a class="btn btn-secondary" href="https://github.com/opensourcepos/opensourcepos/issues/new" target="_blank" rel="noopener"><i class="bi bi-flag"></i> <?= lang('Config.report_an_issue') ?></a>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div style="text-align: center;">
|
<script type="text/javascript">
|
||||||
<a class="copy" data-clipboard-action="copy" data-clipboard-target="#issuetemplate">Copy Info</a> | <a href="https://github.com/opensourcepos/opensourcepos/issues/new" target="_blank"> <?= lang('Config.report_an_issue') ?></a>
|
var clipboard = new ClipboardJS('.copy');
|
||||||
<script type="text/javascript">
|
|
||||||
var clipboard = new ClipboardJS('.copy');
|
|
||||||
|
|
||||||
clipboard.on('success', function(e) {
|
clipboard.on('success', function(e) {
|
||||||
document.getSelection().removeAllRanges();
|
document.getSelection().removeAllRanges();
|
||||||
|
$.notify({
|
||||||
|
icon: 'bi bi-clipboard-check-fill',
|
||||||
|
message: 'System info successfully copied.'
|
||||||
|
}, {
|
||||||
|
type: 'success'
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
$(function() {
|
clipboard.on('error', function(e) {
|
||||||
$('#timezone').clone().appendTo('#timezoneE');
|
$.notify({
|
||||||
|
icon: 'bi bi-clipboard-x-fill',
|
||||||
|
message: 'Something went wrong while copying.'
|
||||||
|
}, {
|
||||||
|
type: 'danger'
|
||||||
});
|
});
|
||||||
|
});
|
||||||
|
|
||||||
if ($('#timezone').html() !== $('#ostimezone').html()) {
|
document.getElementById("timezone").innerText = Intl.DateTimeFormat().resolvedOptions().timeZone;
|
||||||
document.getElementById("timezone").innerText = Intl.DateTimeFormat().resolvedOptions().timeZone;
|
|
||||||
document.getElementById("TimeError").innerHTML = '<span style="color: red;"><?= lang('Config.timezone_error') ?></span><br><br><?= lang('Config.user_timezone') ?><div id="timezoneE" style="font-weight:600;"></div><br><?= lang('Config.os_timezone') ?><div id="ostimezoneE" style="font-weight:600;"><?= esc($config['timezone']) ?></div><br>';
|
$(function() {
|
||||||
}
|
$('#timezone').clone().appendTo('#timezoneE');
|
||||||
</script>
|
});
|
||||||
</div>
|
|
||||||
|
if ($('#timezone').html() !== $('#ostimezone').html()) {
|
||||||
|
$('#time-error').removeClass('d-none');
|
||||||
|
};
|
||||||
|
</script>
|
||||||
|
|||||||
@@ -5,38 +5,28 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveTables/', ['id' => 'table_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveTables/', ['id' => 'table_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="table_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.table_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="table_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.dinner_table_enable'), 'dinner_table_enable', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'dinner_table_enable',
|
|
||||||
'value' => 'dinner_table_enable',
|
|
||||||
'id' => 'dinner_table_enable',
|
|
||||||
'checked' => $config['dinner_table_enable'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div id="dinner_tables">
|
<div class="form-check form-switch mb-3">
|
||||||
<?= view('partial/dinner_tables', ['dinner_tables' => $dinner_tables]) ?>
|
<input class="form-check-input" type="checkbox" role="switch" id="dinner_table_enable" name="dinner_table_enable" value="dinner_table_enable" <?= $config['dinner_table_enable'] == 1 ? 'checked' : '' ?>>
|
||||||
</div>
|
<label class="form-check-label" for="dinner_table_enable"><?= lang('Config.dinner_table_enable'); ?></label>
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_table',
|
|
||||||
'id' => 'submit_table',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="row" id="dinner_tables">
|
||||||
|
<?= view('partial/dinner_tables', ['dinner_tables' => $dinner_tables]) ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_table"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -72,8 +62,8 @@
|
|||||||
var block = $(this).parent().clone(true);
|
var block = $(this).parent().clone(true);
|
||||||
var new_block = block.insertAfter($(this).parent());
|
var new_block = block.insertAfter($(this).parent());
|
||||||
var new_block_id = 'dinner_table_' + ++id;
|
var new_block_id = 'dinner_table_' + ++id;
|
||||||
$(new_block).find('label').html("<?= lang('Config.dinner_table') ?> " + ++table_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2');
|
$(new_block).find('label').html("<?= lang('Config.dinner_table') ?> " + ++table_count).attr('for', new_block_id).attr('class', 'control-label col-xs-2'); // TODO-BS5 change classes from bs3 to bs5
|
||||||
$(new_block).find('input').attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val('');
|
$(new_block).find('input').attr('id', new_block_id).removeAttr('disabled').attr('name', new_block_id).attr('class', 'form-control input-sm').val(''); // TODO-BS5 change classes from bs3 to bs5
|
||||||
hide_show_remove();
|
hide_show_remove();
|
||||||
};
|
};
|
||||||
|
|
||||||
@@ -114,6 +104,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
|
|||||||
@@ -8,136 +8,99 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<?= form_open('config/saveTax/', ['id' => 'tax_config_form', 'class' => 'form-horizontal']) ?>
|
<?= form_open('config/saveTax/', ['id' => 'tax_config_form']) ?>
|
||||||
<div id="config_wrapper">
|
|
||||||
<fieldset id="config_info">
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?php
|
||||||
<ul id="tax_error_message_box" class="error_message_box"></ul>
|
$title_info['config_title'] = lang('Config.tax_configuration');
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<ul id="error_message_box" class="tax_error_message_box alert alert-warning d-none"></ul>
|
||||||
<?= form_label(lang('Config.tax_id'), 'tax_id', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
<div class="row">
|
||||||
<?= form_input([
|
<div class="col-12 col-lg-6">
|
||||||
'name' => 'tax_id',
|
<label for="tax_id" class="form-label"><?= lang('Config.tax_id'); ?></label>
|
||||||
'id' => 'tax_id',
|
<div class="input-group mb-3">
|
||||||
'class' => 'form-control input-sm',
|
<span class="input-group-text"><i class="bi bi-bank"></i></span>
|
||||||
'value' => $config['tax_id']
|
<input type="text" name="tax_id" class="form-control" id="tax_id" value="<?= $config['tax_id']; ?>">
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.tax_included'), 'tax_included', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'tax_included',
|
|
||||||
'id' => 'tax_included',
|
|
||||||
'value' => 'tax_included',
|
|
||||||
'checked' => $config['tax_included'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_tax_rate_1'), 'default_tax_1_rate', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_tax_1_name',
|
|
||||||
'id' => 'default_tax_1_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['default_tax_1_name'] !== false ? $config['default_tax_1_name'] : lang('Items.sales_tax_1')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-1 input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_tax_1_rate',
|
|
||||||
'id' => 'default_tax_1_rate',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_tax_decimals($config['default_tax_1_rate'])
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">%</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_tax_rate_2'), 'default_tax_2_rate', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_tax_2_name',
|
|
||||||
'id' => 'default_tax_2_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $config['default_tax_2_name'] !== false ? $config['default_tax_2_name'] : lang('Items.sales_tax_2')
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-1 input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'default_tax_2_rate',
|
|
||||||
'id' => 'default_tax_2_rate',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_tax_decimals($config['default_tax_2_rate'])
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm">%</span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.use_destination_based_tax'), 'use_destination_based_tax', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'use_destination_based_tax',
|
|
||||||
'id' => 'use_destination_based_tax',
|
|
||||||
'value' => 'use_destination_based_tax',
|
|
||||||
'checked' => $config['use_destination_based_tax'] == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_tax_code'), 'default_tax_code', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'default_tax_code',
|
|
||||||
$tax_code_options,
|
|
||||||
$config['default_tax_code'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_tax_category'), 'default_tax_category', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'default_tax_category',
|
|
||||||
$tax_category_options,
|
|
||||||
$config['default_tax_category'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Config.default_tax_jurisdiction'), 'default_tax_jurisdiction', ['class' => 'control-label col-xs-2']) ?>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'default_tax_jurisdiction',
|
|
||||||
$tax_jurisdiction_options,
|
|
||||||
$config['default_tax_jurisdiction'],
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_submit([
|
|
||||||
'name' => 'submit_tax',
|
|
||||||
'id' => 'submit_tax',
|
|
||||||
'value' => lang('Common.submit'),
|
|
||||||
'class' => 'btn btn-primary btn-sm pull-right'
|
|
||||||
]) ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="tax_included" name="tax_included" <?= $config['tax_included'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="tax_included"><?= lang('Config.tax_included'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="default_tax_1_rate" class="form-label"><?= lang('Config.default_tax_rate_1') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-1-square"></i></span>
|
||||||
|
<input type="text" class="form-control w-25" id="default_tax_1_name" name="default_tax_1_name" value="<?= $config['default_tax_1_name'] !== false ? $config['default_tax_1_name'] : lang('Items.sales_tax_1') ?>">
|
||||||
|
<input type="number" step="any" min="0" max="100" class="form-control" id="default_tax_1_rate" name="default_tax_1_rate" value="<?= to_tax_decimals($config['default_tax_1_rate']) ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-percent"></i></span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="default_tax_2_rate" class="form-label"><?= lang('Config.default_tax_rate_2') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-2-square"></i></span>
|
||||||
|
<input type="text" class="form-control w-25" id="default_tax_2_name" name="default_tax_2_name" value="<?= $config['default_tax_2_name'] !== false ? $config['default_tax_2_name'] : lang('Items.sales_tax_2') ?>">
|
||||||
|
<input type="number" step="any" min="0" max="100" class="form-control" id="default_tax_2_rate" name="default_tax_2_rate" value="<?= to_tax_decimals($config['default_tax_2_rate']) ?>">
|
||||||
|
<span class="input-group-text"><i class="bi bi-percent"></i></span>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="form-check form-switch mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" role="switch" id="use_destination_based_tax" name="use_destination_based_tax" value="use_destination_based_tax" <?= $config['use_destination_based_tax'] == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="use_destination_based_tax"><?= lang('Config.use_destination_based_tax'); ?></label>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="row">
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="default_tax_code" class="form-label"><?= lang('Config.default_tax_code'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-code"></i></span>
|
||||||
|
<select class="form-select" name="default_tax_code" id="default_tax_code">
|
||||||
|
<?php foreach ($tax_code_options as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $config['default_tax_code'] == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="default_tax_category" class="form-label"><?= lang('Config.default_tax_category'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-bookmark"></i></span>
|
||||||
|
<select class="form-select" name="default_tax_category" id="default_tax_category">
|
||||||
|
<?php foreach ($tax_category_options as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $config['default_tax_category'] == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="col-12 col-lg-6">
|
||||||
|
<label for="default_tax_jurisdiction" class="form-label"><?= lang('Config.default_tax_jurisdiction'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-globe"></i></span>
|
||||||
|
<select class="form-select" name="default_tax_jurisdiction" id="default_tax_jurisdiction">
|
||||||
|
<?php foreach ($tax_jurisdiction_options as $key => $value): ?>
|
||||||
|
<option value="<?= $key ?>" <?= $config['default_tax_jurisdiction'] == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="d-flex justify-content-end">
|
||||||
|
<button type="submit" class="btn btn-primary" name="submit_tax"><?= lang('Common.submit'); ?></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -168,6 +131,7 @@
|
|||||||
},
|
},
|
||||||
success: function(response) {
|
success: function(response) {
|
||||||
$.notify({
|
$.notify({
|
||||||
|
icon: 'bi bi-bell-fill',
|
||||||
message: response.message
|
message: response.message
|
||||||
}, {
|
}, {
|
||||||
type: response.success ? 'success' : 'danger'
|
type: response.success ? 'success' : 'danger'
|
||||||
|
|||||||
@@ -11,433 +11,239 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("$controller_name/save/$person_info->person_id", ['id' => 'customer_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("$controller_name/save/$person_info->person_id", ['id' => 'customer_form', 'class' => 'form-horizontal']) ?>
|
<?php if (!empty($stats) || (!empty($mailchimp_info) && !empty($mailchimp_activity))) { ?>
|
||||||
|
<ul class="nav nav-pills nav-justified mb-3" role="tablist">
|
||||||
|
<li class="nav-item" role="presentation">
|
||||||
|
<button type="button" class="nav-link active" data-bs-toggle="pill" data-bs-target="#customer_basic_info" role="tab"><?= lang('Customers.basic_information') ?></button>
|
||||||
|
</li>
|
||||||
|
<?php if (!empty($stats)) { ?>
|
||||||
|
<li class="nav-item" role="presentation">
|
||||||
|
<button type="button" class="nav-link" data-bs-toggle="pill" data-bs-target="#customer_stats_info" role="tab"><?= lang('Customers.stats_info') ?></button>
|
||||||
|
</li>
|
||||||
|
<?php } ?>
|
||||||
|
<?php if (!empty($mailchimp_info) && !empty($mailchimp_activity)) { ?>
|
||||||
|
<li class="nav-item" role="presentation">
|
||||||
|
<button type="button" class="nav-link" data-bs-toggle="pill" data-bs-target="#customer_mailchimp_info" role="tab"><?= lang('Customers.mailchimp_info') ?></button>
|
||||||
|
</li>
|
||||||
|
<?php } ?>
|
||||||
|
</ul>
|
||||||
|
<?php } ?>
|
||||||
|
|
||||||
<ul class="nav nav-tabs nav-justified" data-tabs="tabs">
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<li class="active" role="presentation">
|
|
||||||
<a data-toggle="tab" href="#customer_basic_info"><?= lang('Customers.basic_information') ?></a>
|
|
||||||
</li>
|
|
||||||
<?php if (!empty($stats)) { ?>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#customer_stats_info"><?= lang('Customers.stats_info') ?></a>
|
|
||||||
</li>
|
|
||||||
<?php } ?>
|
|
||||||
<?php if (!empty($mailchimp_info) && !empty($mailchimp_activity)) { ?>
|
|
||||||
<li role="presentation">
|
|
||||||
<a data-toggle="tab" href="#customer_mailchimp_info"><?= lang('Customers.mailchimp_info') ?></a>
|
|
||||||
</li>
|
|
||||||
<?php } ?>
|
|
||||||
</ul>
|
|
||||||
|
|
||||||
<div class="tab-content">
|
<div class="tab-content">
|
||||||
<div class="tab-pane fade in active" id="customer_basic_info">
|
<div class="tab-pane show active" id="customer_basic_info" role="tabpanel" tabindex="0">
|
||||||
<fieldset>
|
<div class="form-check mb-3">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="checkbox" name="consent" id="consent" value="1" required <?php $checked = ($person_info->consent == '' ? !$config['enforce_privacy'] : (bool)$person_info->consent); if ($checked) { echo 'checked';} ?>>
|
||||||
<?= form_label(lang('Customers.consent'), 'consent', ['class' => 'required control-label col-xs-3']) ?>
|
<label class="form-check-label" for="consent"><?= lang('Customers.consent') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="col-xs-1">
|
</div>
|
||||||
<?= form_checkbox('consent', 1, $person_info->consent == '' ? !$config['enforce_privacy'] : (bool)$person_info->consent) ?>
|
|
||||||
</div>
|
<?= view('people/form_basic_info') ?>
|
||||||
|
|
||||||
|
<label for="discount_type" class="form-label"><?= lang('Customers.discount_type') ?></label>
|
||||||
|
<div class="mb-3">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="discount_type" id="discount_type_percent" value="0" <?php if ($person_info->discount_type == PERCENT) echo 'checked'; ?>>
|
||||||
|
<label class="form-check-label" for="discount_type_percent"><?= lang('Customers.discount_percent') ?></label>
|
||||||
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="discount_type" id="discount_type_fixed" value="1" <?php if ($person_info->discount_type == FIXED) echo 'checked'; ?>>
|
||||||
|
<label class="form-check-label" for="discount_type_fixed"><?= lang('Customers.discount_fixed') ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="discount" class="form-label"><?= lang('Customers.discount'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="discount-icon"><i class="bi bi-patch-minus"></i></span>
|
||||||
|
<input type="number" step="any" class="form-control" name="discount" id="discount" aria-describedby="discount-icon" value="<?= $person_info->discount_type === FIXED ? to_currency_no_money($person_info->discount) : to_decimals($person_info->discount)?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="company_name" class="form-label"><?= lang('Customers.company_name'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="company_name-icon"><i class="bi bi-building"></i></span>
|
||||||
|
<input type="text" class="form-control" name="company_name" id="company_name" aria-describedby="company_name-icon" value="<?= $person_info->company_name ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="account_number" class="form-label"><?= lang('Customers.account_number'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="account_number-icon"><i class="bi bi-hash"></i></span>
|
||||||
|
<input type="text" class="form-control" name="account_number" id="account_number" aria-describedby="account_number-icon" value="<?= $person_info->account_number ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="tax_id" class="form-label"><?= lang('Customers.tax_id'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="tax_id-icon"><i class="bi bi-bank"></i></span>
|
||||||
|
<input type="text" class="form-control" name="tax_id" id="tax_id" aria-describedby="tax_id-icon" value="<?= $person_info->tax_id ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<?php if ($config['customer_reward_enable']): ?>
|
||||||
|
<label for="rewards" class="form-label"><?= lang('Customers.rewards_package'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-trophy"></i></span>
|
||||||
|
<select class="form-select" name="package_id">
|
||||||
|
<?php foreach ($packages as $id => $label): ?>
|
||||||
|
<option value="<?= $id ?>" <?= $id == $selected_package ? 'selected' : '' ?>><?= $label ?></option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<?= view('people/form_basic_info') ?>
|
<label for="available_points" class="form-label"><?= lang('Customers.available_points'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
<div class="form-group form-group-sm">
|
<span class="input-group-text" id="available_points-icon"><i class="bi bi-hand-thumbs-up"></i></span>
|
||||||
<?= form_label(lang('Customers.discount_type'), 'discount_type', ['class' => 'control-label col-xs-3']) ?>
|
<input type="text" class="form-control" name="available_points" id="available_points" aria-describedby="available_points-icon" value="<?= $person_info->points ?>" disabled readonly>
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'discount_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'discount_type',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $person_info->discount_type == PERCENT
|
|
||||||
]) ?> <?= lang('Customers.discount_percent') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'discount_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'discount_type',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $person_info->discount_type == FIXED
|
|
||||||
]) ?> <?= lang('Customers.discount_fixed') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="form-check mb-3">
|
||||||
<?= form_label(lang('Customers.discount'), 'discount', ['class' => 'control-label col-xs-3']) ?>
|
<input class="form-check-input" type="checkbox" name="taxable" id="taxable" value="1" <?php if ($person_info->taxable == 1) echo 'checked'; ?>>
|
||||||
<div class="col-xs-3">
|
<label class="form-check-label" for="taxable"><?= lang('Customers.taxable') ?></label>
|
||||||
<div class="input-group input-group-sm">
|
</div>
|
||||||
<?= form_input([
|
|
||||||
'name' => 'discount',
|
<?php if ($use_destination_based_tax): ?>
|
||||||
'id' => 'discount',
|
<label for="sales_tax_code_name" class="form-label"><?= lang('Customers.tax_code'); ?></label>
|
||||||
'class' => 'form-control input-sm',
|
<div class="input-group mb-3">
|
||||||
'onClick' => 'this.select();',
|
<span class="input-group-text" id="sales_tax_code_name-icon"><i class="bi bi-bank"></i></span>
|
||||||
'value' => $person_info->discount_type === FIXED ? to_currency_no_money($person_info->discount) : to_decimals($person_info->discount)
|
<input type="hidden" name="sales_tax_code_id" value="<?= $person_info->sales_tax_code_id ?>">
|
||||||
]) ?>
|
<input type="text" class="form-control" name="sales_tax_code_name" id="sales_tax_code_name" aria-describedby="sales_tax_code_name-icon" size="50" value="<?= $sales_tax_code_label ?>">
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="datetime" class="form-label"><?= lang('Customers.date'); ?></label>
|
||||||
<?= form_label(lang('Customers.company_name'), 'customer_company_name', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="datetime-icon"><i class="bi bi-calendar2"></i></span>
|
||||||
<?= form_input([
|
<input type="hidden" name="date" id="datetime" aria-describedby="datetime-icon" value="<?= to_datetime(strtotime($person_info->date)) ?>">
|
||||||
'name' => 'company_name',
|
<input type="text" class="form-control" value="<?= to_datetime(strtotime($person_info->date)) ?>" disabled readonly>
|
||||||
'id' => 'customer_company_name',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->company_name
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="employee" class="form-label"><?= lang('Customers.employee'); ?></label>
|
||||||
<?= form_label(lang('Customers.account_number'), 'account_number', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="employee-icon"><i class="bi bi-person"></i></span>
|
||||||
<?= form_input([
|
<input type="hidden" name="employee_id" value="<?= $person_info->employee_id ?>">
|
||||||
'name' => 'account_number',
|
<input type="text" class="form-control" name="employee" id="employee" aria-describedby="employee-icon" value="<?= $employee ?>" disabled readonly>
|
||||||
'id' => 'account_number',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->account_number
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.tax_id'), 'tax_id', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_id',
|
|
||||||
'id' => 'tax_id',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->tax_id
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php if ($config['customer_reward_enable']): ?>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.rewards_package'), 'rewards', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_dropdown(
|
|
||||||
'package_id',
|
|
||||||
$packages,
|
|
||||||
$selected_package,
|
|
||||||
'class="form-control input-sm"'
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.available_points'), 'available_points', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'available_points',
|
|
||||||
'id' => 'available_points',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->points,
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php endif; ?>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.taxable'), 'taxable', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox('taxable', 1, $person_info->taxable == 1) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php if ($use_destination_based_tax) { ?>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.tax_code'), 'sales_tax_code_name', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'sales_tax_code_name',
|
|
||||||
'id' => 'sales_tax_code_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'size' => '50',
|
|
||||||
'value' => $sales_tax_code_label
|
|
||||||
]) ?>
|
|
||||||
<?= form_hidden('sales_tax_code_id', $person_info->sales_tax_code_id) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.date'), 'date', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-calendar"></span></span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'date',
|
|
||||||
'id' => 'datetime',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_datetime(strtotime($person_info->date)),
|
|
||||||
'readonly' => 'true'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Customers.employee'), 'employee', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'employee',
|
|
||||||
'id' => 'employee',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $employee,
|
|
||||||
'readonly' => 'true'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= form_hidden('employee_id', $person_info->employee_id) ?>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<?php if (!empty($stats)) { ?>
|
<?php if (!empty($stats)) { ?>
|
||||||
<br>
|
<div class="tab-pane" id="customer_stats_info" role="tabpanel" tabindex="0">
|
||||||
<div class="tab-pane" id="customer_stats_info">
|
<label for="total" class="form-label"><?= lang('Customers.total'); ?></label>
|
||||||
<fieldset>
|
<div class="input-group mb-3">
|
||||||
<div class="form-group form-group-sm">
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
<?= form_label(lang('Customers.total'), 'total', ['class' => 'control-label col-xs-5']) ?>
|
<span class="input-group-text" id="total-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<div class="col-xs-4">
|
<?php endif; ?>
|
||||||
<div class="input-group input-group-sm">
|
<input type="text" class="form-control" name="total" id="total" aria-describedby="total-icon" value="<?= to_currency_no_money($stats->total) ?>" disabled readonly>
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
<span class="input-group-text" id="total-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
<?= form_input([
|
</div>
|
||||||
'name' => 'total',
|
|
||||||
'id' => 'total',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($stats->total),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="max" class="form-label"><?= lang('Customers.max'); ?></label>
|
||||||
<?= form_label(lang('Customers.max'), 'max', ['class' => 'control-label col-xs-5']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
<div class="input-group input-group-sm">
|
<span class="input-group-text" id="max-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
<?php endif; ?>
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
<input type="text" class="form-control" name="max" id="max" aria-describedby="max-icon" value="<?= to_currency_no_money($stats->max) ?>" disabled readonly>
|
||||||
<?php endif; ?>
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
<?= form_input([
|
<span class="input-group-text" id="max-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
'name' => 'max',
|
<?php endif; ?>
|
||||||
'id' => 'max',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($stats->max),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="min" class="form-label"><?= lang('Customers.min'); ?></label>
|
||||||
<?= form_label(lang('Customers.min'), 'min', ['class' => 'control-label col-xs-5']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
<div class="input-group input-group-sm">
|
<span class="input-group-text" id="min-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
<?php endif; ?>
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
<input type="text" class="form-control" name="min" id="min" aria-describedby="min-icon" value="<?= to_currency_no_money($stats->min) ?>" disabled readonly>
|
||||||
<?php endif; ?>
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
<?= form_input([
|
<span class="input-group-text" id="min-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
'name' => 'min',
|
<?php endif; ?>
|
||||||
'id' => 'min',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($stats->min),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="average" class="form-label"><?= lang('Customers.average'); ?></label>
|
||||||
<?= form_label(lang('Customers.average'), 'average', ['class' => 'control-label col-xs-5']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
<div class="input-group input-group-sm">
|
<span class="input-group-text" id="average-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
<?php endif; ?>
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
<input type="text" class="form-control" name="average" id="average" aria-describedby="average-icon" value="<?= to_currency_no_money($stats->average) ?>" disabled readonly>
|
||||||
<?php endif; ?>
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
<?= form_input([
|
<span class="input-group-text" id="average-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
'name' => 'average',
|
<?php endif; ?>
|
||||||
'id' => 'average',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($stats->average),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="quantity" class="form-label"><?= lang('Customers.quantity'); ?></label>
|
||||||
<?= form_label(lang('Customers.quantity'), 'quantity', ['class' => 'control-label col-xs-5']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="quantity-icon"><i class="bi bi-123"></i></span>
|
||||||
<div class="input-group input-group-sm">
|
<input type="text" class="form-control" name="quantity" id="quantity" aria-describedby="quantity-icon" value="<?= to_quantity_decimals($stats->quantity) ?>" disabled readonly>
|
||||||
<span class="input-group-addon input-sm"><b><?= '>' ?></b></span>
|
</div>
|
||||||
<?= form_input([
|
|
||||||
'name' => 'quantity',
|
|
||||||
'id' => 'quantity',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_quantity_decimals($stats->quantity),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="avg_discount" class="form-label"><?= lang('Customers.avg_discount'); ?></label>
|
||||||
<?= form_label(lang('Customers.avg_discount'), 'avg_discount', ['class' => 'control-label col-xs-5']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="avg_discount-icon"><i class="bi bi-percent"></i></span>
|
||||||
<div class="input-group input-group-sm">
|
<input type="text" class="form-control" name="avg_discount" id="avg_discount" aria-describedby="avg_discount-icon" value="<?= to_decimals($stats->avg_discount) ?>" disabled readonly>
|
||||||
<?= form_input([
|
</div>
|
||||||
'name' => 'avg_discount',
|
|
||||||
'id' => 'avg_discount',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_decimals($stats->avg_discount),
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm"><b>%</b></span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
<?php } ?>
|
<?php } ?>
|
||||||
|
|
||||||
<?php if (!empty($mailchimp_info) && !empty($mailchimp_activity)) { ?>
|
<?php if (!empty($mailchimp_info) && !empty($mailchimp_activity)) { ?>
|
||||||
<div class="tab-pane" id="customer_mailchimp_info">
|
<div class="tab-pane" id="customer_mailchimp_info" role="tabpanel" tabindex="0">
|
||||||
<fieldset>
|
<label for="mailchimp_status" class="form-label"><?= lang('Customers.mailchimp_status'); ?></label>
|
||||||
<div class="form-group form-group-sm">
|
<div class="input-group mb-3">
|
||||||
<?= form_label(lang('Customers.mailchimp_status'), 'mailchimp_status', ['class' => 'control-label col-xs-3']) ?>
|
<span class="input-group-text"><i class="bi bi-envelope-check"></i></span>
|
||||||
<div class="col-xs-4">
|
<select class="form-select" name="mailchimp_status" id="mailchimp_status">
|
||||||
<?= form_dropdown(
|
<option value="subscribed" <?= $mailchimp_info['status'] === 'subscribed' ? 'selected' : '' ?>>Subscribed</option>
|
||||||
'mailchimp_status',
|
<option value="unsubscribed" <?= $mailchimp_info['status'] === 'unsubscribed' ? 'selected' : '' ?>>Unsubscribed</option>
|
||||||
[
|
<option value="cleaned" <?= $mailchimp_info['status'] === 'cleaned' ? 'selected' : '' ?>>Cleaned</option>
|
||||||
'subscribed' => 'subscribed',
|
<option value="pending" <?= $mailchimp_info['status'] === 'pending' ? 'selected' : '' ?>>Pending</option>
|
||||||
'unsubscribed' => 'unsubscribed',
|
</select>
|
||||||
'cleaned' => 'cleaned',
|
</div>
|
||||||
'pending' => 'pending'
|
|
||||||
],
|
|
||||||
$mailchimp_info['status'],
|
|
||||||
['id' => 'mailchimp_status', 'class' => 'form-control input-sm']
|
|
||||||
) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="form-check mb-3">
|
||||||
<?= form_label(lang('Customers.mailchimp_vip'), 'mailchimp_vip', ['class' => 'control-label col-xs-3']) ?>
|
<input class="form-check-input" type="checkbox" name="mailchimp_vip" id="mailchimp_vip" value="1" <?= $mailchimp_info['vip'] == 1 ? 'checked' : '' ?>>
|
||||||
<div class="col-xs-1">
|
<label class="form-check-label" for="mailchimp_vip"><?= lang('Customers.mailchimp_vip') ?></label>
|
||||||
<?= form_checkbox('mailchimp_vip', 1, $mailchimp_info['vip'] == 1) ?>
|
</div>
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_member_rating" class="form-label"><?= lang('Customers.mailchimp_member_rating'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_member_rating'), 'mailchimp_member_rating', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_member_rating-icon"><i class="bi bi-hand-thumbs-up"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_member_rating" id="mailchimp_member_rating" aria-describedby="mailchimp_member_rating-icon" value="<?= $mailchimp_info['member_rating'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_member_rating',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_info['member_rating'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_activity_total" class="form-label"><?= lang('Customers.mailchimp_activity_total'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_activity_total'), 'mailchimp_activity_total', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_activity_total-icon"><i class="bi bi-envelope-arrow-up"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_activity_total" id="mailchimp_activity_total" aria-describedby="mailchimp_activity_total-icon" value="<?= $mailchimp_activity['total'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_activity_total',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_activity['total'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_activity_lastopen" class="form-label"><?= lang('Customers.mailchimp_activity_lastopen'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_activity_lastopen'), 'mailchimp_activity_lastopen', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_activity_lastopen-icon"><i class="bi bi-calendar2-check"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_activity_lastopen" id="mailchimp_activity_lastopen" aria-describedby="mailchimp_activity_lastopen-icon" value="<?= $mailchimp_activity['lastopen'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_activity_lastopen',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_activity['lastopen'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_activity_open" class="form-label"><?= lang('Customers.mailchimp_activity_open'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_activity_open'), 'mailchimp_activity_open', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_activity_open-icon"><i class="bi bi-envelope-open"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_activity_open" id="mailchimp_activity_open" aria-describedby="mailchimp_activity_open-icon" value="<?= $mailchimp_activity['open'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_activity_open',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_activity['open'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_activity_click" class="form-label"><?= lang('Customers.mailchimp_activity_click'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_activity_click'), 'mailchimp_activity_click', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_activity_click-icon"><i class="bi bi-hand-index"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_activity_click" id="mailchimp_activity_click" aria-describedby="mailchimp_activity_click-icon" value="<?= $mailchimp_activity['click'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_activity_click',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_activity['click'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_activity_unopen" class="form-label"><?= lang('Customers.mailchimp_activity_unopen'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_activity_unopen'), 'mailchimp_activity_unopen', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_activity_unopen-icon"><i class="bi bi-envelope-slash"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_activity_unopen" id="mailchimp_activity_unopen" aria-describedby="mailchimp_activity_unopen-icon" value="<?= $mailchimp_activity['unopen'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_activity_unopen',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_activity['unopen'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="mailchimp_email_client" class="form-label"><?= lang('Customers.mailchimp_email_client'); ?></label>
|
||||||
<?= form_label(lang('Customers.mailchimp_email_client'), 'mailchimp_email_client', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="mailchimp_email_client-icon"><i class="bi bi-inbox"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="mailchimp_email_client" id="mailchimp_email_client" aria-describedby="mailchimp_email_client-icon" value="<?= $mailchimp_info['email_client'] ?>" disabled readonly>
|
||||||
'name' => 'mailchimp_email_client',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $mailchimp_info['email_client'],
|
|
||||||
'disabled' => ''
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
<?php } ?>
|
<?php } ?>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -1,27 +1,22 @@
|
|||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
<?= form_open_multipart('customers/importCsvFile/', ['id' => 'csv_form']) ?>
|
||||||
|
|
||||||
<?= form_open_multipart('customers/importCsvFile/', ['id' => 'csv_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="item_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<a type="button" class="btn btn-secondary mb-3" href="<?= esc('customers/csv') ?>"><?= lang('Common.download_import_template') ?></a>
|
||||||
<div class="col-xs-12">
|
|
||||||
<a href="<?= esc('customers/csv') ?>"><?= lang('Common.download_import_template') ?></a>
|
<div class="fileinput fileinput-new input-group mb-3" data-provides="fileinput">
|
||||||
</div>
|
<span class="input-group-text"><i class="bi bi-filetype-csv"></i></span>
|
||||||
|
<div class="form-control" data-trigger="fileinput">
|
||||||
|
<span class="fileinput-filename"></span>
|
||||||
</div>
|
</div>
|
||||||
|
<span class="input-group-text fileinput-exists" data-dismiss="fileinput" style="cursor: pointer;"><?= lang('Common.import_remove_file') ?></span>
|
||||||
|
<span class="input-group-text btn-file">
|
||||||
|
<span class="fileinput-new"><?= lang('Common.import_select_file') ?></span>
|
||||||
|
<span class="fileinput-exists"><?= lang('Common.import_change_file') ?></span>
|
||||||
|
<input type="file" id="file_path" name="file_path" accept=".csv">
|
||||||
|
</span>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<div class="col-xs-12">
|
|
||||||
<div class="fileinput fileinput-new input-group" data-provides="fileinput">
|
|
||||||
<div class="form-control" data-trigger="fileinput"><i class="glyphicon glyphicon-file fileinput-exists"></i><span class="fileinput-filename"></span></div>
|
|
||||||
<span class="input-group-addon input-sm btn btn-default btn-file">
|
|
||||||
<span class="fileinput-new"><?= lang('Common.import_select_file') ?></span><span class="fileinput-exists"><?= lang('Common.import_change_file') ?></span><input type="file" id="file_path" name="file_path" accept=".csv">
|
|
||||||
</span>
|
|
||||||
<a href="#" class="input-group-addon input-sm btn btn-default fileinput-exists" data-dismiss="fileinput"><?= lang('Common.import_remove_file') ?></a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
@@ -8,152 +8,125 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("$controller_name/save/$person_info->person_id", ['id' => 'employee_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("$controller_name/save/$person_info->person_id", ['id' => 'employee_form', 'class' => 'form-horizontal']) ?>
|
<ul class="nav nav-pills nav-justified mb-3" role="tablist">
|
||||||
|
<li class="nav-item" role="presentation">
|
||||||
<ul class="nav nav-tabs nav-justified" data-tabs="tabs">
|
<button type="button" class="nav-link active" data-bs-toggle="pill" data-bs-target="#employee_basic_info" role="tab"><?= lang('Employees.basic_information') ?></button>
|
||||||
<li class="active" role="presentation">
|
|
||||||
<a data-toggle="tab" href="#employee_basic_info"><?= lang('Employees.basic_information') ?></a>
|
|
||||||
</li>
|
</li>
|
||||||
<li role="presentation">
|
<li class="nav-item" role="presentation">
|
||||||
<a data-toggle="tab" href="#employee_login_info"><?= lang('Employees.login_info') ?></a>
|
<button type="button" class="nav-link" data-bs-toggle="pill" data-bs-target="#employee_login_info" role="tab"><?= lang('Employees.login_info') ?></button>
|
||||||
</li>
|
</li>
|
||||||
<li role="presentation">
|
<li class="nav-item" role="presentation">
|
||||||
<a data-toggle="tab" href="#employee_permission_info"><?= lang('Employees.permission_info') ?></a>
|
<button type="button" class="nav-link" data-bs-toggle="pill" data-bs-target="#employee_permission_info" role="tab"><?= lang('Employees.permission_info') ?></button>
|
||||||
</li>
|
</li>
|
||||||
</ul>
|
</ul>
|
||||||
|
|
||||||
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
|
|
||||||
<div class="tab-content">
|
<div class="tab-content">
|
||||||
<div class="tab-pane fade in active" id="employee_basic_info">
|
<div class="tab-pane show active" id="employee_basic_info" role="tabpanel" tabindex="0">
|
||||||
<fieldset>
|
<?= view('people/form_basic_info') ?>
|
||||||
<?= view('people/form_basic_info') ?>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="tab-pane" id="employee_login_info">
|
<div class="tab-pane" id="employee_login_info" role="tabpanel" tabindex="0">
|
||||||
<fieldset>
|
<label for="username" class="form-label"><?= lang('Employees.username'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="form-group form-group-sm">
|
<div class="input-group mb-3">
|
||||||
<?= form_label(lang('Employees.username'), 'username', ['class' => 'required control-label col-xs-3']) ?>
|
<span class="input-group-text" id="username-icon"><i class="bi bi-person"></i></span>
|
||||||
<div class="col-xs-8">
|
<input type="text" class="form-control" name="username" id="username" aria-describedby="username-icon" value="<?= $person_info->username; ?>" required>
|
||||||
<div class="input-group">
|
</div>
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-user"></span></span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'username',
|
|
||||||
'id' => 'username',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->username
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php $password_label_attributes = $person_info->person_id == "" ? ['class' => 'required'] : []; ?>
|
<?php $password_label_attributes = $person_info->person_id == "" ? ['class' => 'required'] : []; ?>
|
||||||
|
<label for="password" class="form-label"><?= lang('Employees.password'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="password-icon"><i class="bi bi-lock"></i></span>
|
||||||
|
<input type="password" class="form-control" name="password" id="password" aria-describedby="password-icon" required>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="repeat_password" class="form-label"><?= lang('Employees.repeat_password'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<?= form_label(lang('Employees.password'), 'password', array_merge($password_label_attributes, ['class' => 'control-label col-xs-3'])) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="repeat_password-icon"><i class="bi bi-lock"></i></span>
|
||||||
<div class="input-group">
|
<input type="password" class="form-control" name="repeat_password" id="repeat_password" aria-describedby="repeat_password-icon" required>
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-lock"></span></span>
|
</div>
|
||||||
<?= form_password([
|
|
||||||
'name' => 'password',
|
|
||||||
'id' => 'password',
|
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="language" class="form-label"><?= lang('Employees.language'); ?></label>
|
||||||
<?= form_label(lang('Employees.repeat_password'), 'repeat_password', array_merge($password_label_attributes, ['class' => 'control-label col-xs-3'])) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="language-icon"><i class="bi bi-globe"></i></span>
|
||||||
<div class="input-group">
|
<?php
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-lock"></span></span>
|
$languages = get_languages();
|
||||||
<?= form_password([
|
$languages[':'] = lang('Employees.system_language');
|
||||||
'name' => 'repeat_password',
|
$language_code = current_language_code();
|
||||||
'id' => 'repeat_password',
|
$language = current_language();
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
// If No language is set then it will display "System Language"
|
||||||
<?= form_label(lang('Employees.language'), 'language', ['class' => 'control-label col-xs-3']) ?>
|
if ($language_code === current_language_code(true)) {
|
||||||
<div class="col-xs-8">
|
$language_code = '';
|
||||||
<div class="input-group">
|
$language = '';
|
||||||
<?php
|
}
|
||||||
$languages = get_languages();
|
|
||||||
$languages[':'] = lang('Employees.system_language');
|
|
||||||
$language_code = current_language_code();
|
|
||||||
$language = current_language();
|
|
||||||
|
|
||||||
// If No language is set then it will display "System Language"
|
echo form_dropdown(
|
||||||
if ($language_code === current_language_code(true)) {
|
'language',
|
||||||
$language_code = '';
|
$languages,
|
||||||
$language = '';
|
"$language_code:$language",
|
||||||
}
|
['class' => 'form-select']
|
||||||
|
);
|
||||||
echo form_dropdown(
|
?>
|
||||||
'language',
|
</div>
|
||||||
$languages,
|
|
||||||
"$language_code:$language",
|
|
||||||
['class' => 'form-control input-sm']
|
|
||||||
);
|
|
||||||
?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="tab-pane" id="employee_permission_info">
|
<div class="tab-pane" id="employee_permission_info" role="tabpanel" tabindex="0">
|
||||||
<fieldset>
|
<div class="mb-3"><?= lang('Employees.permission_desc') ?></div>
|
||||||
<p><?= lang('Employees.permission_desc') ?></p>
|
<ul class="list-unstyled" id="permission_list">
|
||||||
|
<?php foreach ($all_modules as $module): ?>
|
||||||
|
<li class="form-check">
|
||||||
|
<input class="form-check-input module" type="checkbox" value="<?= $module->module_id ?>" name="grant_<?= $module->module_id ?>" id="grant_<?= $module->module_id ?>" <?= $module->grant == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="grant_<?= $module->module_id ?>">
|
||||||
|
<select class="form-select form-select-sm d-inline-block w-auto me-1 module" name="menu_group_<?= $module->module_id ?>">
|
||||||
|
<option value="home" <?= $module->menu_group == 'home' ? 'selected' : '' ?>>
|
||||||
|
<?= lang('Module.home') ?>
|
||||||
|
</option>
|
||||||
|
<option value="office" <?= $module->menu_group == 'office' ? 'selected' : '' ?>>
|
||||||
|
<?= lang('Module.office') ?>
|
||||||
|
</option>
|
||||||
|
<option value="both" <?= $module->menu_group == 'both' ? 'selected' : '' ?>>
|
||||||
|
<?= lang('Module.both') ?>
|
||||||
|
</option>
|
||||||
|
</select>
|
||||||
|
<span><?= lang("Module.$module->module_id") ?>:</span>
|
||||||
|
<span class="fw-light fst-italic"><?= lang("Module.$module->module_id" . '_desc') ?></span>
|
||||||
|
</label>
|
||||||
|
|
||||||
<ul id="permission_list">
|
<?php foreach ($all_subpermissions as $permission): ?>
|
||||||
<?php foreach ($all_modules as $module) { ?>
|
|
||||||
<li>
|
|
||||||
<?= form_checkbox("grant_$module->module_id", $module->module_id, $module->grant == 1, 'class="module"') ?>
|
|
||||||
<?= form_dropdown(
|
|
||||||
"menu_group_$module->module_id",
|
|
||||||
[
|
|
||||||
'home' => lang('Module.home'),
|
|
||||||
'office' => lang('Module.office'),
|
|
||||||
'both' => lang('Module.both')
|
|
||||||
],
|
|
||||||
$module->menu_group,
|
|
||||||
'class="module"'
|
|
||||||
) ?>
|
|
||||||
|
|
||||||
<span class="medium"><?= lang("Module.$module->module_id") ?>:</span>
|
|
||||||
<span class="small"><?= lang("Module.$module->module_id" . '_desc') ?></span>
|
|
||||||
<?php
|
<?php
|
||||||
foreach ($all_subpermissions as $permission) {
|
|
||||||
$exploded_permission = explode('_', $permission->permission_id, 2);
|
$exploded_permission = explode('_', $permission->permission_id, 2);
|
||||||
if ($permission->module_id == $module->module_id) {
|
|
||||||
$lang_key = $module->module_id . '.' . $exploded_permission[1];
|
if ($permission->module_id != $module->module_id) {
|
||||||
$lang_line = lang(ucfirst($lang_key));
|
continue;
|
||||||
$lang_line = (lang(ucfirst($lang_key)) == $lang_line) ? ucwords(str_replace("_", " ", $exploded_permission[1])) : $lang_line;
|
}
|
||||||
if (!empty($lang_line)) {
|
|
||||||
?>
|
$lang_key = $module->module_id . '.' . $exploded_permission[1];
|
||||||
<ul>
|
$lang_line = lang(ucfirst($lang_key));
|
||||||
<li>
|
|
||||||
<?= form_checkbox("grant_$permission->permission_id", $permission->permission_id, $permission->grant == 1) ?>
|
// Fallback if language line doesn't exist
|
||||||
<?= form_hidden("menu_group_$permission->permission_id", "--") ?>
|
if ($lang_line === lang(ucfirst($lang_key))) {
|
||||||
<span class="medium"><?= esc($lang_line) ?></span>
|
$lang_line = ucwords(str_replace("_", " ", $exploded_permission[1]));
|
||||||
</li>
|
}
|
||||||
</ul>
|
|
||||||
<?php
|
if (empty($lang_line)) {
|
||||||
}
|
continue;
|
||||||
}
|
}
|
||||||
}
|
|
||||||
?>
|
?>
|
||||||
</li>
|
<ul class="list-unstyled">
|
||||||
<?php } ?>
|
<li class="form-check">
|
||||||
</ul>
|
<input class="form-check-input module" type="checkbox" value="<?= $permission->permission_id ?>" name="grant_<?= $permission->permission_id ?>" id="grant_<?= $permission->permission_id ?>" <?= $permission->grant == 1 ? 'checked' : '' ?>>
|
||||||
</fieldset>
|
<input type="hidden" name="menu_group_<?= $permission->permission_id ?>" value="--">
|
||||||
|
<label class="form-check-label" for="grant_<?= $permission->permission_id ?>"><?= esc($lang_line) ?></label>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</li>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</ul>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
|
|||||||
@@ -101,9 +101,11 @@ p.lead {
|
|||||||
}
|
}
|
||||||
|
|
||||||
.tabs {
|
.tabs {
|
||||||
list-style: none inside none;
|
list-style: none;
|
||||||
|
list-style-position: inside;
|
||||||
|
margin: 0;
|
||||||
padding: 0;
|
padding: 0;
|
||||||
margin: 0 0 -1px;
|
margin-bottom: -1px;
|
||||||
}
|
}
|
||||||
.tabs li {
|
.tabs li {
|
||||||
display: inline;
|
display: inline;
|
||||||
|
|||||||
@@ -9,159 +9,109 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("expenses/save/$expenses_info->expense_id", ['id' => 'expenses_edit_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("expenses/save/$expenses_info->expense_id", ['id' => 'expenses_edit_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="item_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="mb-3"><?= lang('Expenses.info') ?> <?= !empty($expenses_info->expense_id) ? lang('Expenses.expense_id') . " $expenses_info->expense_id" : '' ?></div>
|
||||||
<?= form_label(lang('Expenses.info'), 'expenses_info', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<?= form_label(!empty($expenses_info->expense_id) ? lang('Expenses.expense_id') . " $expenses_info->expense_id" : '', 'expenses_info_id', ['class' => 'control-label col-xs-8', 'style' => 'text-align: left']) ?>
|
<label for="datetime" class="form-label"><?= lang('Expenses.date'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="datetime-icon"><i class="bi bi-calendar2"></i></span>
|
||||||
|
<input type="hidden" name="date" id="datetime" aria-describedby="datetime-icon" value="<?= to_datetime(strtotime($expenses_info->date)) ?>">
|
||||||
|
<input type="text" class="form-control" value="<?= to_datetime(strtotime($expenses_info->date)) ?>" disabled readonly>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="supplier_name" class="form-label"><?= lang('Expenses.supplier_name'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="supplier_name-icon"><i class="bi bi-truck"></i></span>
|
||||||
|
<input type="hidden" name="supplier_id" id="supplier_id">
|
||||||
|
<input type="text" class="form-control" name="supplier_name" id="supplier_name" aria-describedby="supplier_name-icon" value="<?= lang('Expenses.start_typing_supplier_name') ?>">
|
||||||
|
<button type="button" class="btn btn-outline-danger" id="remove_supplier_button" title="Remove Supplier"><i class="bi bi-x-circle"></i></button>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="supplier_tax_code" class="form-label"><?= lang('Expenses.supplier_tax_code'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="supplier_tax_code-icon"><i class="bi bi-piggy-bank"></i></span>
|
||||||
|
<input type="text" class="form-control" name="supplier_tax_code" id="supplier_tax_code" aria-describedby="supplier_tax_code-icon" value="<?= $expenses_info->supplier_tax_code ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="amount" class="form-label"><?= lang('Expenses.amount'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="amount" id="amount" aria-describedby="amount-icon" value="<?= to_currency_no_money($expenses_info->amount) ?>" required>
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="tax_amount" class="form-label"><?= lang('Expenses.tax_amount'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="tax_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input class="form-control" name="tax_amount" id="tax_amount" aria-describedby="tax_amount-icon" value="<?= to_currency_no_money($expenses_info->tax_amount) ?>">
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="tax_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="payment_type" class="form-label"><?= lang('Expenses.payment'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="payment_type-icon"><i class="bi bi-wallet2"></i></span>
|
||||||
|
<select class="form-select" name="payment_type" id="payment_type" aria-describedby="payment_type-icon">
|
||||||
|
<?php foreach ($payment_options as $k => $v): ?>
|
||||||
|
<option value="<?= $k ?>" <?= $k == $expenses_info->payment_type ? 'selected' : '' ?>>
|
||||||
|
<?= $v ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="category" class="form-label"><?= lang('Expenses_categories.name'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="category-icon"><i class="bi bi-bookmark"></i></span>
|
||||||
|
<select class="form-select" name="expense_category_id" id="category" aria-describedby="category-icon">
|
||||||
|
<?php foreach ($expense_categories as $k => $v): ?>
|
||||||
|
<option value="<?= $k ?>" <?= $k == $expenses_info->expense_category_id ? 'selected' : '' ?>>
|
||||||
|
<?= $v ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="employee" class="form-label"><?= lang('Expenses.employee'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="employee-icon"><i class="bi bi-person"></i></span>
|
||||||
|
<?php if ($can_assign_employee): ?>
|
||||||
|
<select class="form-select" name="employee_id" id="employee_id">
|
||||||
|
<?php foreach ($employees as $k => $v): ?>
|
||||||
|
<option value="<?= $k ?>" <?= $k == $expenses_info->employee_id ? 'selected' : '' ?>>
|
||||||
|
<?= esc($v) ?>
|
||||||
|
</option>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
</select>
|
||||||
|
<?php else: ?>
|
||||||
|
<input type="hidden" name="employee_id" value="<?= $expenses_info->employee_id ?>">
|
||||||
|
<input type="text" class="form-control" name="employee" id="employee" aria-describedby="employee-icon" value="<?= esc($employees[$expenses_info->employee_id] ?? '') ?>" disabled readonly>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="description" class="form-label"><?= lang('Expenses.description'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-chat"></i></span>
|
||||||
|
<textarea class="form-control" name="description" id="description" rows="6"><?= $expenses_info->description ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<?php if (!empty($expenses_info->expense_id)): ?>
|
||||||
|
<div class="form-check mb-3">
|
||||||
|
<input class="form-check-input" type="checkbox" name="deleted" id="deleted" value="1" <?= $expenses_info->deleted == 1 ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label text-danger" for="deleted"><?= lang('Expenses.is_deleted') ?></label>
|
||||||
</div>
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.date'), 'date', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-calendar"></span></span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'date',
|
|
||||||
'class' => 'form-control input-sm datetime',
|
|
||||||
'value' => to_datetime(strtotime($expenses_info->date)),
|
|
||||||
'readonly' => 'readonly'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.supplier_name'), 'supplier_name', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'supplier_name',
|
|
||||||
'id' => 'supplier_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => lang('Expenses.start_typing_supplier_name')
|
|
||||||
]);
|
|
||||||
echo form_input([
|
|
||||||
'type' => 'hidden',
|
|
||||||
'name' => 'supplier_id',
|
|
||||||
'id' => 'supplier_id'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-2">
|
|
||||||
<a id="remove_supplier_button" class="btn btn-danger btn-sm" title="Remove Supplier">
|
|
||||||
<span class="glyphicon glyphicon-remove"></span>
|
|
||||||
</a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.supplier_tax_code'), 'supplier_tax_code', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'supplier_tax_code',
|
|
||||||
'id' => 'supplier_tax_code',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $expenses_info->supplier_tax_code
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.amount'), 'amount', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'amount',
|
|
||||||
'id' => 'amount',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($expenses_info->amount)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.tax_amount'), 'tax_amount', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_amount',
|
|
||||||
'id' => 'tax_amount',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($expenses_info->tax_amount)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.payment'), 'payment_type', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_dropdown('payment_type', $payment_options, $expenses_info->payment_type, ['class' => 'form-control', 'id' => 'payment_type']) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses_categories.name'), 'category', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_dropdown('expense_category_id', $expense_categories, $expenses_info->expense_category_id, ['class' => 'form-control', 'id' => 'category']) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.employee'), 'employee', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?php if ($can_assign_employee): ?>
|
|
||||||
<?= form_dropdown('employee_id', $employees, $expenses_info->employee_id, 'id="employee_id" class="form-control"') ?>
|
|
||||||
<?php else: ?>
|
|
||||||
<?= form_hidden('employee_id', $expenses_info->employee_id) ?>
|
|
||||||
<?= form_input(['name' => 'employee_name', 'value' => esc($employees[$expenses_info->employee_id] ?? ''), 'class' => 'form-control', 'readonly' => 'readonly']) ?>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.description'), 'description', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-6">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'description',
|
|
||||||
'id' => 'description',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $expenses_info->description
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php if (!empty($expenses_info->expense_id)) { ?>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Expenses.is_deleted') . ':', 'deleted', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-5">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'deleted',
|
|
||||||
'id' => 'deleted',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $expenses_info->deleted == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
@@ -12,6 +12,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Expenses';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
// Load the preset datarange picker
|
// Load the preset datarange picker
|
||||||
@@ -54,29 +59,36 @@
|
|||||||
|
|
||||||
<?= view('partial/print_receipt', ['print_after_sale' => false, 'selected_printer' => 'takings_printer']) ?>
|
<?= view('partial/print_receipt', ['print_after_sale' => false, 'selected_printer' => 'takings_printer']) ?>
|
||||||
|
|
||||||
<div id="title_bar" class="print_hide btn-toolbar">
|
<div id="title_bar" class="d-flex gap-2 justify-content-end d-print-none">
|
||||||
<button onclick="printdoc()" class="btn btn-info btn-sm pull-right">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= "$controller_name/view" ?>" title="<?= lang(ucfirst($controller_name) . ".new") ?>">
|
||||||
<span class="glyphicon glyphicon-print"> </span><?= lang('Common.print') ?>
|
<i class="bi bi-journal-check me-2"></i><?= lang(esc(ucfirst($controller_name)) . '.new') // TODO: String Interpolation ?>
|
||||||
</button>
|
</button>
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= "$controller_name/view" ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
<button type="button" class="btn btn-primary" onclick="window.print()" title="<?= lang('Common.print') ?>">
|
||||||
<span class="glyphicon glyphicon-tags"> </span><?= lang(ucfirst($controller_name) . '.new') ?>
|
<i class="bi bi-printer me-2"></i><?= lang('Common.print') ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left form-inline" role="toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm print_hide">
|
<button type="button" id="delete" class="btn btn-secondary d-print-none">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
<?= form_input(['name' => 'daterangepicker', 'class' => 'form-control input-sm', 'id' => 'daterangepicker']) ?>
|
|
||||||
<?= form_multiselect('filters[]', esc($filters), $selected_filters ?? [], [
|
<div class="input-group w-auto">
|
||||||
'id' => 'filters',
|
<span class="input-group-text" id="daterangepicker-icon"><i class="bi bi-calendar2-range"></i></span>
|
||||||
'data-none-selected-text' => lang('Common.none_selected_text'),
|
<input type="text" class="form-select" name="daterangepicker" id="daterangepicker" aria-describedby="daterangepicker-icon">
|
||||||
'class' => 'selectpicker show-menu-arrow',
|
</div>
|
||||||
'data-selected-text-format' => 'count > 1',
|
|
||||||
'data-style' => 'btn-default btn-sm',
|
<div class="input-group w-auto">
|
||||||
'data-width' => 'fit'
|
<span class="input-group-text" id="filters-icon"><i class="bi bi-funnel"></i></span>
|
||||||
]) ?>
|
<select class="form-select" name="filters[]" id="filters" aria-describedby="filters-icon" multiple>
|
||||||
|
<?php foreach (esc($filters) as $value => $label) { ?>
|
||||||
|
<option value="<?= $value ?>" <?= in_array($value, $selected_filters ?? []) ? 'selected' : '' ?>>
|
||||||
|
<?= $label ?>
|
||||||
|
</option>
|
||||||
|
<?php } ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
@@ -87,3 +99,15 @@
|
|||||||
<div id="payment_summary"></div>
|
<div id="payment_summary"></div>
|
||||||
|
|
||||||
<?= view('partial/footer') ?>
|
<?= view('partial/footer') ?>
|
||||||
|
|
||||||
|
<script type="text/javascript">
|
||||||
|
new TomSelect('#filters', {
|
||||||
|
plugins: ['checkbox_options', 'remove_button'],
|
||||||
|
placeholder: '<?= lang('Common.none_selected_text') ?>',
|
||||||
|
hidePlaceholder: true,
|
||||||
|
closeAfterSelect: false,
|
||||||
|
onChange: function() {
|
||||||
|
$('#table').bootstrapTable('refresh');
|
||||||
|
}
|
||||||
|
});
|
||||||
|
</script>
|
||||||
|
|||||||
@@ -5,37 +5,22 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("expenses_categories/save/$category_info->expense_category_id", ['id' => 'expense_category_edit_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("expenses_categories/save/$category_info->expense_category_id", ['id' => 'expense_category_edit_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="expenses_categories">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="category_name" class="form-label"><?= lang('Expenses_categories.name'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<?= form_label(lang('Expenses_categories.name'), 'category_name', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="category_name-icon"><i class="bi bi-bookmark"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="category_name" id="category_name" aria-describedby="category_name-icon" value="<?= $category_info->category_name; ?>" required>
|
||||||
'name' => 'category_name',
|
</div>
|
||||||
'id' => 'category_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $category_info->category_name
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="category_description" class="form-label"><?= lang('Expenses_categories.description'); ?></label>
|
||||||
<?= form_label(lang('Expenses_categories.description'), 'category_description', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="category_description-icon"><i class="bi bi-card-text"></i></span>
|
||||||
<?= form_textarea([
|
<textarea class="form-control" name="category_description" id="category_description" rows="10" aria-describedby="category_description-icon"><?= $category_info->category_description ?></textarea>
|
||||||
'name' => 'category_description',
|
</div>
|
||||||
'id' => 'category_description',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $category_info->category_description
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
@@ -8,6 +8,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Expenses Categories';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
<?= view('partial/bootstrap_tables_locale') ?>
|
<?= view('partial/bootstrap_tables_locale') ?>
|
||||||
@@ -27,16 +32,16 @@
|
|||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div id="title_bar" class="btn-toolbar">
|
<div class="d-flex gap-2 justify-content-end">
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
||||||
<span class="glyphicon glyphicon-list"> </span><?= lang(ucfirst($controller_name) . '.new') ?>
|
<i class="bi bi-bookmark-plus me-2"></i><?= lang(ucfirst($controller_name) . '.new') ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left form-inline" role="toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm print_hide">
|
<button type="button" class="btn btn-secondary" id="delete">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -10,65 +10,42 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("giftcards/save/$giftcard_id", ['id' => 'giftcard_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("giftcards/save/$giftcard_id", ['id' => 'giftcard_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="giftcard_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="person_name" class="form-label"><?= lang('Giftcards.person_id'); ?></label>
|
||||||
<?= form_label(lang('Giftcards.person_id'), 'person_name', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="person_name-icon"><i class="bi bi-person"></i></span>
|
||||||
<?= form_input([
|
<input type="hidden" name="person_id" value="<?= (string)$selected_person_id ?>">
|
||||||
'name' => 'person_name',
|
<input type="text" class="form-control" name="person_name" id="person_name" aria-describedby="person_name-icon" value="<?= $selected_person_name ?>">
|
||||||
'id' => 'person_name',
|
</div>
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $selected_person_name
|
|
||||||
]) ?>
|
|
||||||
<?= form_hidden('person_id', (string)$selected_person_id) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php
|
<?php
|
||||||
$class = '';
|
$class = '';
|
||||||
if ($config['giftcard_number'] == 'series') {
|
$label = '';
|
||||||
$class = ' required';
|
if ($config['giftcard_number'] == 'series') {
|
||||||
}
|
$class = 'required';
|
||||||
?>
|
$label = '<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup>';
|
||||||
<div class="form-group form-group-sm">
|
}
|
||||||
<?= form_label(lang('Giftcards.giftcard_number'), 'giftcard_number', ['class' => "control-label col-xs-3$class"]) ?>
|
?>
|
||||||
<div class="col-xs-4">
|
<label for="giftcard_number" class="form-label"><?= lang('Giftcards.giftcard_number'); ?><?= $label ?></label>
|
||||||
<?= form_input([
|
<div class="input-group mb-3">
|
||||||
'name' => 'giftcard_number',
|
<span class="input-group-text" id="giftcard_number-icon"><i class="bi bi-gift"></i></span>
|
||||||
'id' => 'giftcard_number',
|
<input type="text" class="form-control" name="giftcard_number" id="giftcard_number" aria-describedby="giftcard_number-icon" value="<?= $giftcard_number ?>" <?= $class ?>>
|
||||||
'class' => 'form-control input-sm',
|
</div>
|
||||||
'value' => $giftcard_number
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
|
<label for="giftcard_amount" class="form-label"><?= lang('Giftcards.card_value') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="giftcard_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
<input type="number" class="form-control" name="giftcard_amount" id="giftcard_amount" aria-describedby="giftcard_amount-icon" value="<?= number_format((float)$giftcard_value, 2, '.', '') ?>" required>
|
||||||
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="giftcard_amount-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Giftcards.card_value'), 'giftcard_amount', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><?= esc($config['currency_symbol']) ?></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'giftcard_amount',
|
|
||||||
'id' => 'giftcard_amount',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => to_currency_no_money($giftcard_value)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
@@ -8,6 +8,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Gift Cards';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
<?= view('partial/bootstrap_tables_locale') ?>
|
<?= view('partial/bootstrap_tables_locale') ?>
|
||||||
@@ -20,16 +25,16 @@
|
|||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div id="title_bar" class="btn-toolbar">
|
<div class="d-flex gap-2 justify-content-end">
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
||||||
<span class="glyphicon glyphicon-heart"> </span><?= lang(ucfirst($controller_name) . '.new') ?>
|
<i class="bi bi-gift me-2"></i><?= lang(ucfirst($controller_name) .'.new') ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left btn-toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm">
|
<button type="button" class="btn btn-secondary">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -1,130 +0,0 @@
|
|||||||
<?php
|
|
||||||
/**
|
|
||||||
* @var object $person_info
|
|
||||||
*/
|
|
||||||
?>
|
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("home/save/$person_info->person_id", ['id' => 'employee_form', 'class' => 'form-horizontal']) ?>
|
|
||||||
<div class="tab-content">
|
|
||||||
<div class="tab-pane fade in active" id="employee_login_info">
|
|
||||||
<fieldset>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Employees.username'), 'username', ['class' => 'required control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-user"></span></span>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'username',
|
|
||||||
'id' => 'username',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $person_info->username,
|
|
||||||
'readonly' => 'true'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php $password_label_attributes = $person_info->person_id == "" ? ['class' => 'required'] : []; ?>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Employees.current_password'), 'current_password', array_merge($password_label_attributes, ['class' => 'control-label col-xs-3'])) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-lock"></span></span>
|
|
||||||
<?= form_password([
|
|
||||||
'name' => 'current_password',
|
|
||||||
'id' => 'current_password',
|
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Employees.password'), 'password', array_merge($password_label_attributes, ['class' => 'control-label col-xs-3'])) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-lock"></span></span>
|
|
||||||
<?= form_password([
|
|
||||||
'name' => 'password',
|
|
||||||
'id' => 'password',
|
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Employees.repeat_password'), 'repeat_password', array_merge($password_label_attributes, ['class' => 'control-label col-xs-3'])) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-lock"></span></span>
|
|
||||||
<?= form_password([
|
|
||||||
'name' => 'repeat_password',
|
|
||||||
'id' => 'repeat_password',
|
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?= form_close() ?>
|
|
||||||
|
|
||||||
<script type="text/javascript">
|
|
||||||
// Validation and submit handling
|
|
||||||
$(document).ready(function() {
|
|
||||||
$.validator.setDefaults({
|
|
||||||
ignore: []
|
|
||||||
});
|
|
||||||
|
|
||||||
$.validator.addMethod("notEqualTo", function(value, element, param) {
|
|
||||||
return this.optional(element) || value != $(param).val();
|
|
||||||
}, '<?= lang('Employees.password_not_must_match') ?>');
|
|
||||||
|
|
||||||
$('#employee_form').validate($.extend({
|
|
||||||
submitHandler: function(form) {
|
|
||||||
$(form).ajaxSubmit({
|
|
||||||
success: function(response) {
|
|
||||||
dialog_support.hide();
|
|
||||||
$.notify(response.message, {
|
|
||||||
type: response.success ? 'success' : 'danger'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
dataType: 'json'
|
|
||||||
});
|
|
||||||
},
|
|
||||||
|
|
||||||
rules: {
|
|
||||||
current_password: {
|
|
||||||
required: true,
|
|
||||||
minlength: 8
|
|
||||||
},
|
|
||||||
password: {
|
|
||||||
required: true,
|
|
||||||
minlength: 8,
|
|
||||||
notEqualTo: "#current_password"
|
|
||||||
},
|
|
||||||
repeat_password: {
|
|
||||||
equalTo: "#password"
|
|
||||||
}
|
|
||||||
},
|
|
||||||
|
|
||||||
messages: {
|
|
||||||
password: {
|
|
||||||
required: "<?= lang('Employees.password_required') ?>",
|
|
||||||
minlength: "<?= lang('Employees.password_minlength') ?>"
|
|
||||||
},
|
|
||||||
repeat_password: {
|
|
||||||
equalTo: "<?= lang('Employees.password_must_match') ?>"
|
|
||||||
}
|
|
||||||
}
|
|
||||||
}, form_support.error));
|
|
||||||
});
|
|
||||||
</script>
|
|
||||||
@@ -6,19 +6,6 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<?= view('home/modules') ?>
|
||||||
dialog_support.init("a.modal-dlg");
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<h3 class="text-center"><?= lang('Common.welcome_message') ?></h3>
|
|
||||||
|
|
||||||
<div id="home_module_list">
|
|
||||||
<?php foreach($allowed_modules as $module) { ?>
|
|
||||||
<div class="module_item" title="<?= lang("Module.$module->module_id" . '_desc') ?>">
|
|
||||||
<a href="<?= base_url($module->module_id) ?>"><img src="<?= base_url("images/menubar/$module->module_id.svg") ?>" style="border-width: 0; height: 64px; max-width: 64px;" alt="Menubar Image"></a>
|
|
||||||
<a href="<?= base_url($module->module_id) ?>"><?= lang("Module.$module->module_id") ?></a>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= view('partial/footer') ?>
|
<?= view('partial/footer') ?>
|
||||||
|
|||||||
16
app/Views/home/modules.php
Normal file
16
app/Views/home/modules.php
Normal file
@@ -0,0 +1,16 @@
|
|||||||
|
<h3 class="text-center pb-3 d-none d-lg-block"><?= lang('Common.welcome_message') ?></h3>
|
||||||
|
|
||||||
|
<section class="container-fluid d-flex flex-wrap justify-content-center gap-3 p-0 py-1 py-lg-0">
|
||||||
|
<?php foreach ($allowed_modules as $module) { ?>
|
||||||
|
<div class="border border-primary rounded shadow-sm bg-primary-subtle text-center d-block" title="<?= lang("Module.$module->module_id" . '_desc') ?>">
|
||||||
|
<a href="<?= base_url($module->module_id) ?>">
|
||||||
|
<img class="d-block mx-auto p-2" src="<?= base_url("images/menubar/$module->module_id.svg") ?>" alt="Menubar Image"> <!-- TODO-BS5 alt text translatable -->
|
||||||
|
</a>
|
||||||
|
<a href="<?= base_url($module->module_id) ?>">
|
||||||
|
<div class="tile-text rounded-bottom d-block bg-primary text-light fw-bold p-2">
|
||||||
|
<span><?= lang("Module.$module->module_id") ?></span>
|
||||||
|
</div>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
<?php } ?>
|
||||||
|
</section>
|
||||||
@@ -6,19 +6,6 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<?= view('home/modules') ?>
|
||||||
dialog_support.init("a.modal-dlg");
|
|
||||||
</script>
|
|
||||||
|
|
||||||
<h3 class="text-center"><?= lang('Common.welcome_message') ?></h3>
|
|
||||||
|
|
||||||
<div id="office_module_list">
|
|
||||||
<?php foreach ($allowed_modules as $module) { ?>
|
|
||||||
<div class="module_item" title="<?= lang("Module.$module->module_id" . '_desc') ?>">
|
|
||||||
<a href="<?= base_url($module->module_id) ?>"><img src="<?= base_url("images/menubar/$module->module_id.svg") ?>" style="border-width: 0; height: 64px; max-width: 64px;" alt="Menubar Image"></a>
|
|
||||||
<a href="<?= base_url($module->module_id) ?>"><?= lang("Module.$module->module_id") ?></a>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?= view('partial/footer') ?>
|
<?= view('partial/footer') ?>
|
||||||
|
|||||||
137
app/Views/home/profile.php
Normal file
137
app/Views/home/profile.php
Normal file
@@ -0,0 +1,137 @@
|
|||||||
|
<?php
|
||||||
|
$email = $user_info->email;
|
||||||
|
$size = 96;
|
||||||
|
$default = 'https://ui-avatars.com/api/?name=' . $user_info->first_name . '+' . $user_info->last_name . '&format=svg&size=' . $size;
|
||||||
|
$grav_url = 'https://www.gravatar.com/avatar/' . md5(strtolower(trim($email))) . '?d=' . urlencode($default) . '&s=' . $size;
|
||||||
|
?>
|
||||||
|
|
||||||
|
<div class="modal fade" id="profile-modal" tabindex="-1" aria-hidden="true">
|
||||||
|
<div class="modal-dialog">
|
||||||
|
<div class="modal-content">
|
||||||
|
<div class="modal-header">
|
||||||
|
<ul class="nav nav-pills nav-justified w-100 me-1 gap-1">
|
||||||
|
<li class="nav-item">
|
||||||
|
<button type="button" id="modal-button-profile" onclick="modalSwitchProfile()" class="nav-link active">Profile</button>
|
||||||
|
</li>
|
||||||
|
<li class="nav-item" title="<?= lang('Employees.change_password'); ?>">
|
||||||
|
<button type="button" id="modal-button-password" onclick="modalSwitchPassword()" class="nav-link"><?= lang('Employees.change_password'); ?></button>
|
||||||
|
</li>
|
||||||
|
</ul>
|
||||||
|
<button type="button" class="btn-close" data-bs-dismiss="modal" aria-label="Close"></button>
|
||||||
|
</div>
|
||||||
|
<div class="modal-body text-start">
|
||||||
|
<div id="modal-profile">
|
||||||
|
<div class="container">
|
||||||
|
<table>
|
||||||
|
<tbody>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-2"><img class="img-thumbnail rounded-circle" src="<?= $default; ?>" style="height: 48px;"></td>
|
||||||
|
<td class="align-middle"><h5><?= $user_info->first_name . ' ' . $user_info->last_name; ?></h5></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
<br>
|
||||||
|
<table>
|
||||||
|
<tbody>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3">Username</td>
|
||||||
|
<td><?= $user_info->username; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.id'); ?></td>
|
||||||
|
<td><?= $user_info->person_id; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.email'); ?></td>
|
||||||
|
<td><?= $user_info->email; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.phone_number'); ?></td>
|
||||||
|
<td><?= $user_info->phone_number; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.gender'); ?></td>
|
||||||
|
<td><?= $user_info->gender; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.address_1'); ?></td>
|
||||||
|
<td><?= $user_info->address_1; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.address_2'); ?></td>
|
||||||
|
<td><?= $user_info->address_2; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.city'); ?></td>
|
||||||
|
<td><?= $user_info->city; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.state'); ?></td>
|
||||||
|
<td><?= $user_info->state; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.zip'); ?></td>
|
||||||
|
<td><?= $user_info->zip; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.country'); ?></td>
|
||||||
|
<td><?= $user_info->country; ?></td>
|
||||||
|
</tr>
|
||||||
|
<tr>
|
||||||
|
<td class="pe-3"><?= lang('Common.comments'); ?></td>
|
||||||
|
<td><?= $user_info->comments; ?></td>
|
||||||
|
</tr>
|
||||||
|
</tbody>
|
||||||
|
</table>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div id="modal-password" class="d-none was-validated" novalidate>
|
||||||
|
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-person"></i></span>
|
||||||
|
<div class="form-floating">
|
||||||
|
<input name="username" id="input-username" type="text" class="form-control" placeholder="<?= lang('Login.username'); ?>" value="<?= $user_info->username; ?>" disabled>
|
||||||
|
<label for="input-username"><?= lang('Login.username'); ?></label>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-lock"></i></span>
|
||||||
|
<div class="form-floating is-invalid">
|
||||||
|
<input name="password-current" id="input-password-current" type="password" class="form-control" placeholder="Current Password" required>
|
||||||
|
<label for="input-password-current">Current Password</label>
|
||||||
|
</div>
|
||||||
|
<div class="invalid-feedback">Please fill in your current password.</div>
|
||||||
|
</div>
|
||||||
|
<div class="form-text">Must be 8-20 characters long</div>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-lock"></i></span>
|
||||||
|
<div class="form-floating is-invalid">
|
||||||
|
<input name="password-new" id="input-password-new" type="password" class="form-control" placeholder="New Password" required>
|
||||||
|
<label for="input-password-new">New Password</label>
|
||||||
|
</div>
|
||||||
|
<div class="invalid-feedback">Please fill in a new password.</div>
|
||||||
|
</div>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-lock"></i></span>
|
||||||
|
<div class="form-floating is-invalid">
|
||||||
|
<input name="password-repeat" id="input-password-repeat" type="password" class="form-control" placeholder="Repeat Password" required>
|
||||||
|
<label for="input-password-repeat">Repeat Password</label>
|
||||||
|
</div>
|
||||||
|
<div class="invalid-feedback">Please repeat the new password.</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
<div class="modal-footer">
|
||||||
|
<button type="button" class="btn btn-secondary" data-bs-dismiss="modal">Cancel</button>
|
||||||
|
<a type="button" id="modal-button-logout" class="btn btn-danger" href="home/logout">
|
||||||
|
<i class="bi bi-power me-2"></i><?= lang('Login.logout'); ?>
|
||||||
|
</a>
|
||||||
|
<button type="button" id="modal-button-save" class="btn btn-primary d-none">
|
||||||
|
<i class="bi bi-floppy me-2"></i>Save
|
||||||
|
</button>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
|
</div>
|
||||||
@@ -8,200 +8,114 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("item_kits/save/$item_kit_info->item_kit_id", ['id' => 'item_kit_form']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("item_kits/save/$item_kit_info->item_kit_id", ['id' => 'item_kit_form', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="item_kit_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="item_kit_number" class="form-label"><?= lang('Item_kits.item_kit_number'); ?></label>
|
||||||
<?= form_label(lang('Item_kits.item_kit_number'), 'item_kit_number', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="item_kit_number-icon"><i class="bi bi-upc-scan"></i></span>
|
||||||
<div class="input-group">
|
<input type="text" class="form-control" name="item_kit_number" id="item_kit_number" aria-describedby="item_kit_number-icon" value="<?= $item_kit_info->item_kit_number ?>">
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-barcode"></span></span>
|
</div>
|
||||||
<?= form_input([
|
|
||||||
'name' => 'item_kit_number',
|
<label for="name" class="form-label"><?= lang('Item_kits.name'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
'id' => 'item_kit_number',
|
<div class="input-group mb-3">
|
||||||
'class' => 'form-control input-sm',
|
<span class="input-group-text" id="name-icon"><i class="bi bi-tags"></i></span>
|
||||||
'value' => $item_kit_info->item_kit_number
|
<input type="text" class="form-control" name="name" id="name" aria-describedby="name-icon" value="<?= $item_kit_info->name ?>" required>
|
||||||
]) ?>
|
</div>
|
||||||
</div>
|
|
||||||
</div>
|
<label for="item_name" class="form-label"><?= lang('Item_kits.find_kit_item'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="item_name-icon"><i class="bi bi-tag"></i></span>
|
||||||
|
<input type="hidden" name="kit_item_id" value="<?= (string)$selected_kit_item_id ?>">
|
||||||
|
<input type="text" class="form-control" name="item_name" id="item_name" aria-describedby="item_name-icon" value="<?= $selected_kit_item ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="kit_discount_type" class="form-label"><?= lang('Item_kits.discount_type') ?></label>
|
||||||
|
<div class="mb-3">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="kit_discount_type" id="kit_discount_type_percent" value="0" <?= $item_kit_info->kit_discount_type == PERCENT ? 'checked' : '' ?>>
|
||||||
|
<label class="form-check-label" for="kit_discount_type_percent"><?= lang('Item_kits.discount_percent') ?></label>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="kit_discount_type" id="kit_discount_type_fixed" value="1" <?= $item_kit_info->kit_discount_type == FIXED ? 'checked' : '' ?>>
|
||||||
<?= form_label(lang('Item_kits.name'), 'name', ['class' => 'required control-label col-xs-3']) ?>
|
<label class="form-check-label" for="kit_discount_type_fixed"><?= lang('Item_kits.discount_fixed') ?></label>
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'name',
|
|
||||||
'id' => 'name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_kit_info->name
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="kit_discount" class="form-label"><?= lang('Item_kits.discount'); ?></label>
|
||||||
<?= form_label(lang('Item_kits.find_kit_item'), 'item_name', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="kit_discount-icon"><i class="bi bi-patch-minus"></i></span>
|
||||||
<div class="input-group input-group-sm">
|
<input type="number" step="any" class="form-control" name="kit_discount" id="kit_discount" aria-describedby="kit_discount-icon" value="<?= $item_kit_info->kit_discount_type === FIXED ? to_currency_no_money($item_kit_info->kit_discount) : to_decimals($item_kit_info->kit_discount) ?>">
|
||||||
<?= form_input([
|
</div>
|
||||||
'name' => 'item_name',
|
|
||||||
'id' => 'item_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'size' => '50',
|
|
||||||
'value' => $selected_kit_item
|
|
||||||
]) ?>
|
|
||||||
<?= form_hidden('kit_item_id', (string)$selected_kit_item_id) ?>
|
|
||||||
|
|
||||||
</div>
|
<label for="price_option" class="form-label"><?= lang('Item_kits.price_option') ?> <?= !empty($basic_version) ? '<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup>' : '' ?></label>
|
||||||
</div>
|
<div class="mb-3">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="price_option" id="price_option_kit_and_components" value="0" <?= $item_kit_info->price_option == PRICE_ALL ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
|
<label class="form-check-label" for="price_option_kit_and_components"><?= lang('Item_kits.kit_and_components') ?></label>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="price_option" id="price_option_kit_only" value="1" <?= $item_kit_info->price_option == PRICE_KIT ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Item_kits.discount_type'), 'kit_discount_type', ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="price_option_kit_only"><?= lang('Item_kits.kit_only') ?></label>
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'kit_discount_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $item_kit_info->kit_discount_type == PERCENT
|
|
||||||
]) ?> <?= lang('Item_kits.discount_percent') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'kit_discount_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_kit_info->kit_discount_type == FIXED
|
|
||||||
]) ?> <?= lang('Item_kits.discount_fixed') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="price_option" id="price_option_kit_and_stock" value="2" <?= $item_kit_info->price_option == PRICE_KIT_ITEMS ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Item_kits.discount'), 'kit_discount', ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="price_option_kit_and_stock"><?= lang('Item_kits.kit_and_stock') ?></label>
|
||||||
<div class="col-xs-3">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'kit_discount',
|
|
||||||
'size' => '5',
|
|
||||||
'maxlength' => '5',
|
|
||||||
'id' => 'kit_discount',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_kit_info->kit_discount_type === FIXED ? to_currency_no_money($item_kit_info->kit_discount) : to_decimals($item_kit_info->kit_discount)
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="print_option" class="form-label"><?= lang('Item_kits.print_option') ?> <?= !empty($basic_version) ? '<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup>' : '' ?></label>
|
||||||
<?= form_label(lang('Item_kits.price_option'), 'price_option', !empty($basic_version) ? ['class' => 'required control-label col-xs-3'] : ['class' => 'control-label col-xs-3']) ?>
|
<div class="mb-3">
|
||||||
<div class="col-xs-8">
|
<div class="form-check form-check-inline">
|
||||||
<label class="radio-inline">
|
<input class="form-check-input" type="radio" name="print_option" id="print_option_all" value="0" <?= $item_kit_info->print_option == PRINT_ALL ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_radio([
|
<label class="form-check-label" for="print_option_all"><?= lang('Item_kits.all') ?></label>
|
||||||
'name' => 'price_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $item_kit_info->price_option == PRICE_ALL
|
|
||||||
]) ?> <?= lang('Item_kits.kit_and_components') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'price_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_kit_info->price_option == PRICE_KIT
|
|
||||||
]) ?> <?= lang('Item_kits.kit_only') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'price_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 2,
|
|
||||||
'checked' => $item_kit_info->price_option == PRICE_KIT_ITEMS // TODO: === for all of these?
|
|
||||||
]) ?> <?= lang('Item_kits.kit_and_stock') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="print_option" id="print_option_priced_only" value="1" <?= $item_kit_info->print_option == PRINT_PRICED ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Item_kits.print_option'), 'print_option', !empty($basic_version) ? ['class' => 'required control-label col-xs-3'] : ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="print_option_priced_only"><?= lang('Item_kits.priced_only') ?></label>
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $item_kit_info->print_option == PRINT_ALL
|
|
||||||
]) ?> <?= lang('Item_kits.all') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_kit_info->print_option == PRINT_PRICED
|
|
||||||
]) ?> <?= lang('Item_kits.priced_only') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'print_option',
|
|
||||||
'type' => 'radio',
|
|
||||||
'value' => 2,
|
|
||||||
'checked' => $item_kit_info->print_option == PRINT_KIT
|
|
||||||
]) ?> <?= lang('Item_kits.kit_only') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="print_option" id="print_option_kit_only" value="2" <?= $item_kit_info->print_option == PRINT_KIT ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<div class="form-group form-group-sm">
|
<label class="form-check-label" for="print_option_kit_only"><?= lang('Item_kits.kit_only') ?></label>
|
||||||
<?= form_label(lang('Item_kits.description'), 'description', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_textarea([
|
|
||||||
'name' => 'description',
|
|
||||||
'id' => 'description',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_kit_info->description
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="description" class="form-label"><?= lang('Item_kits.description'); ?></label>
|
||||||
<?= form_label(lang('Item_kits.add_item'), 'item', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text"><i class="bi bi-chat"></i></span>
|
||||||
<?= form_input([
|
<textarea class="form-control" name="description" id="description" rows="6"><?= $item_kit_info->description ?></textarea>
|
||||||
'name' => 'item',
|
</div>
|
||||||
'id' => 'item',
|
|
||||||
'class' => 'form-control input-sm'
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<table id="item_kit_items" class="table table-striped table-hover">
|
<label for="item" class="form-label"><?= lang('Item_kits.add_item'); ?></label>
|
||||||
<thead>
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="item-icon"><i class="bi bi-tag"></i></span>
|
||||||
|
<input type="text" class="form-control" name="item" id="item" aria-describedby="item-icon">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<div class="table-responsive">
|
||||||
|
<table class="table table-sm table-hover align-middle text-nowrap" id="item_kit_items">
|
||||||
|
<thead class="table-secondary">
|
||||||
<tr>
|
<tr>
|
||||||
<th style="width: 10%;"><?= lang('Common.delete') ?></th>
|
<th scope="col"><?= lang('Common.delete') ?></th>
|
||||||
<th style="width: 10%;"><?= lang('Item_kits.sequence') ?></th>
|
<th scope="col"><?= lang('Item_kits.sequence') ?></th>
|
||||||
<th style="width: 60%;"><?= lang('Item_kits.item') ?></th>
|
<th scope="col"><?= lang('Item_kits.item') ?></th>
|
||||||
<th style="width: 20%;"><?= lang('Item_kits.quantity') ?></th>
|
<th scope="col"><?= lang('Item_kits.quantity') ?></th>
|
||||||
</tr>
|
</tr>
|
||||||
</thead>
|
</thead>
|
||||||
<tbody>
|
<tbody>
|
||||||
<?php foreach ($item_kit_items as $item_kit_item) { ?>
|
<?php foreach ($item_kit_items as $item_kit_item): ?>
|
||||||
<tr>
|
<tr>
|
||||||
<td><a href="#" onclick="return delete_item_kit_row(this);"><span class="glyphicon glyphicon-trash"></span></a></td>
|
<td class="text-center"><a class="text-danger" href="#" onclick="return delete_item_kit_row(this);"><i class="bi bi-trash"></i></a></td>
|
||||||
<td><input class="quantity form-control input-sm" id="item_seq_<?= $item_kit_item['item_id'] ?>" name="item_kit_seq[<?= $item_kit_item['item_id'] ?>]" value="<?= parse_decimals($item_kit_item['kit_sequence'], 0) ?>"></td>
|
<td class="text-center"><input class="quantity form-control" id="item_seq_<?= $item_kit_item['item_id'] ?>" name="item_kit_seq[<?= $item_kit_item['item_id'] ?>]" value="<?= parse_decimals($item_kit_item['kit_sequence'], 0) ?>"></td>
|
||||||
<td><?= esc($item_kit_item['name']) ?></td>
|
<td><?= esc($item_kit_item['name']) ?></td>
|
||||||
<td><input class="quantity form-control input-sm" id="item_qty_<?= $item_kit_item['item_id'] ?>" name="item_kit_qty[<?= $item_kit_item['item_id'] ?>]" value="<?= to_quantity_decimals($item_kit_item['quantity']) ?>"></td>
|
<td class="text-center"><input class="quantity form-control" id="item_qty_<?= $item_kit_item['item_id'] ?>" name="item_kit_qty[<?= $item_kit_item['item_id'] ?>]" value="<?= to_quantity_decimals($item_kit_item['quantity']) ?>"></td>
|
||||||
</tr>
|
</tr>
|
||||||
<?php } ?>
|
<?php endforeach; ?>
|
||||||
</tbody>
|
</tbody>
|
||||||
</table>
|
</table>
|
||||||
|
</div>
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
@@ -218,10 +132,10 @@
|
|||||||
$('#item_kit_item_' + ui.item.value).val(parseFloat($('#item_kit_item_' + ui.item.value).val()) + 1);
|
$('#item_kit_item_' + ui.item.value).val(parseFloat($('#item_kit_item_' + ui.item.value).val()) + 1);
|
||||||
} else {
|
} else {
|
||||||
$('#item_kit_items').append('<tr>' +
|
$('#item_kit_items').append('<tr>' +
|
||||||
'<td><a href="#" onclick="return delete_item_kit_row(this);"><span class="glyphicon glyphicon-trash"></span></a></td>' +
|
'<td class="text-center"><a class="text-danger" href="#" onclick="return delete_item_kit_row(this);"><i class="bi bi-trash"></i></a></td>' +
|
||||||
'<td><input class="quantity form-control input-sm" id="item_seq_' + ui.item.value + '" name="item_kit_seq[' + ui.item.value + ']" value="0"></td>' +
|
'<td class="text-center"><input class="quantity form-control" id="item_seq_' + ui.item.value + '" name="item_kit_seq[' + ui.item.value + ']" value="0"></td>' +
|
||||||
'<td>' + DOMPurify.sanitize(ui.item.label) + '</td>' +
|
'<td>' + DOMPurify.sanitize(ui.item.label) + '</td>' +
|
||||||
'<td><input class="quantity form-control input-sm" id="item_qty_' + ui.item.value + '" name="item_kit_qty[' + ui.item.value + ']" value="1"></td>' +
|
'<td class="text-center"><input class="quantity form-control" id="item_qty_' + ui.item.value + '" name="item_kit_qty[' + ui.item.value + ']" value="1"></td>' +
|
||||||
'</tr>');
|
'</tr>');
|
||||||
}
|
}
|
||||||
$('#item').val('');
|
$('#item').val('');
|
||||||
|
|||||||
@@ -8,6 +8,11 @@
|
|||||||
|
|
||||||
<?= view('partial/header') ?>
|
<?= view('partial/header') ?>
|
||||||
|
|
||||||
|
<?php
|
||||||
|
$title_info['config_title'] = 'Item Kits';
|
||||||
|
echo view('configs/config_header', $title_info);
|
||||||
|
?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
$(document).ready(function() {
|
$(document).ready(function() {
|
||||||
<?= view('partial/bootstrap_tables_locale') ?>
|
<?= view('partial/bootstrap_tables_locale') ?>
|
||||||
@@ -28,20 +33,19 @@
|
|||||||
});
|
});
|
||||||
</script>
|
</script>
|
||||||
|
|
||||||
<div id="title_bar" class="btn-toolbar">
|
<div class="d-flex gap-2 justify-content-end">
|
||||||
<button class="btn btn-info btn-sm pull-right modal-dlg" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
<button type="button" class="btn btn-primary modal-launch" data-btn-submit="<?= lang('Common.submit') ?>" data-href="<?= esc("$controller_name/view") ?>" title="<?= lang(ucfirst($controller_name) . '.new') ?>">
|
||||||
<span class="glyphicon glyphicon-tags"> </span><?= lang(ucfirst($controller_name) . '.new') ?>
|
<i class="bi bi-tags me-2"></i><?= lang(ucfirst($controller_name) . '.new') ?>
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div id="toolbar">
|
<div id="toolbar">
|
||||||
<div class="pull-left btn-toolbar">
|
<div class="d-flex gap-2">
|
||||||
<button id="delete" class="btn btn-default btn-sm">
|
<button type="button" class="btn btn-secondary" id="delete">
|
||||||
<span class="glyphicon glyphicon-trash"> </span><?= lang('Common.delete') ?>
|
<i class="bi bi-trash"></i><span class="d-none d-sm-inline ms-2"><?= lang('Common.delete') ?></span>
|
||||||
</button>
|
</button>
|
||||||
|
<button type="button" class="btn btn-secondary" id="generate_barcodes" data-href="<?= esc("$controller_name/generateBarcodes") ?>" title="<?= lang('Items.generate_barcodes') ?>">
|
||||||
<button id="generate_barcodes" class="btn btn-default btn-sm" data-href="<?= esc("$controller_name/generateBarcodes") ?>">
|
<i class="bi bi-upc-scan"></i><span class="d-none d-sm-inline ms-2"><?= lang('Items.generate_barcodes') ?></span>
|
||||||
<span class="glyphicon glyphicon-barcode"> </span><?= lang('Items.generate_barcodes') ?>
|
|
||||||
</button>
|
</button>
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
|||||||
@@ -25,430 +25,226 @@
|
|||||||
*/
|
*/
|
||||||
?>
|
?>
|
||||||
|
|
||||||
<div id="required_fields_message"><?= lang('Common.fields_required_message') ?></div>
|
<?= form_open("items/save/$item_info->item_id", ['id' => 'item_form', 'enctype' => 'multipart/form-data']) ?>
|
||||||
<ul id="error_message_box" class="error_message_box"></ul>
|
|
||||||
|
|
||||||
<?= form_open("items/save/$item_info->item_id", ['id' => 'item_form', 'enctype' => 'multipart/form-data', 'class' => 'form-horizontal']) ?>
|
<ul id="error_message_box" class="alert alert-warning d-none"></ul>
|
||||||
<fieldset id="item_basic_info">
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="item_number" class="form-label"><?= lang('Items.item_number'); ?></label>
|
||||||
<?= form_label(lang('Items.item_number'), 'item_number', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="item_number-icon"><i class="bi bi-upc-scan"></i></span>
|
||||||
<div class="input-group">
|
<input type="text" class="form-control" name="item_number" id="item_number" aria-describedby="item_number-icon" value="<?= $item_info->item_number ?>">
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-barcode"></span></span>
|
</div>
|
||||||
<?= form_input([
|
|
||||||
'name' => 'item_number',
|
|
||||||
'id' => 'item_number',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_info->item_number
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="name" class="form-label"><?= lang('Items.name'); ?></label>
|
||||||
<?= form_label(lang('Items.name'), 'name', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="name-icon"><i class="bi bi-tag"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control" name="name" id="name" aria-describedby="name-icon" value="<?= $item_info->name ?>">
|
||||||
'name' => 'name',
|
</div>
|
||||||
'id' => 'name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_info->name
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="category" class="form-label"><?= lang('Items.category'); ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<?= form_label(lang('Items.category'), 'category', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="category-icon"><i class="bi bi-bookmark"></i></span>
|
||||||
<div class="input-group">
|
<?php if ($config['category_dropdown']) { ?>
|
||||||
<span class="input-group-addon input-sm"><span class="glyphicon glyphicon-tag"></span></span>
|
<select class="form-select" name="category" id="category" required>
|
||||||
<?php
|
<?php foreach ($categories as $key => $value) { ?>
|
||||||
if ($config['category_dropdown']) {
|
<option value="<?= $key ?>" <?= $selected_category == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
echo form_dropdown('category', $categories, $selected_category, ['class' => 'form-control']);
|
|
||||||
} else {
|
|
||||||
echo form_input([
|
|
||||||
'name' => 'category',
|
|
||||||
'id' => 'category',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_info->category
|
|
||||||
]);
|
|
||||||
}
|
|
||||||
?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div id="attributes">
|
|
||||||
<script type="text/javascript">
|
|
||||||
$('#attributes').load('<?= "items/attributes/$item_info->item_id" ?>');
|
|
||||||
</script>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.stock_type'), 'stock_type', !empty($basic_version) ? ['class' => 'required control-label col-xs-3'] : ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'stock_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'stock_type',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $item_info->stock_type == HAS_STOCK
|
|
||||||
]) ?> <?= lang('Items.stock') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'stock_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'stock_type',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_info->stock_type == HAS_NO_STOCK
|
|
||||||
]) ?><?= lang('Items.nonstock') ?>
|
|
||||||
</label>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.type'), 'item_type', !empty($basic_version) ? ['class' => 'required control-label col-xs-3'] : ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?php
|
|
||||||
$radio_button = [
|
|
||||||
'name' => 'item_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'item_type',
|
|
||||||
'value' => 0,
|
|
||||||
'checked' => $item_info->item_type == ITEM
|
|
||||||
];
|
|
||||||
|
|
||||||
if ($standard_item_locked) {
|
|
||||||
$radio_button['disabled'] = true;
|
|
||||||
}
|
|
||||||
echo form_radio($radio_button) ?> <?= lang('Items.standard') ?>
|
|
||||||
</label>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?php
|
|
||||||
$radio_button = [
|
|
||||||
'name' => 'item_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'item_type',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_info->item_type == ITEM_KIT
|
|
||||||
];
|
|
||||||
|
|
||||||
if ($item_kit_disabled) {
|
|
||||||
$radio_button['disabled'] = true;
|
|
||||||
}
|
|
||||||
echo form_radio($radio_button) ?> <?= lang('Items.kit') ?>
|
|
||||||
</label>
|
|
||||||
<?php if ($config['derive_sale_quantity'] == '1') { ?>
|
|
||||||
<label class="radio-inline">
|
|
||||||
<?= form_radio([
|
|
||||||
'name' => 'item_type',
|
|
||||||
'type' => 'radio',
|
|
||||||
'id' => 'item_type',
|
|
||||||
'value' => 2,
|
|
||||||
'checked' => $item_info->item_type == ITEM_AMOUNT_ENTRY
|
|
||||||
]) ?><?= lang('Items.amount_entry') ?>
|
|
||||||
</label>
|
|
||||||
<?php } ?>
|
<?php } ?>
|
||||||
<?php if ($allow_temp_item == 1) { ?>
|
</select>
|
||||||
<label class="radio-inline">
|
<?php } else { ?>
|
||||||
<?= form_radio([
|
<input type="text" class="form-control" name="category" id="category" aria-describedby="category-icon" value="<?= $item_info->category ?>" required>
|
||||||
'name' => 'item_type',
|
<?php } ?>
|
||||||
'type' => 'radio',
|
</div>
|
||||||
'id' => 'item_type',
|
|
||||||
'value' => 3,
|
<div id="attributes">
|
||||||
'checked' => $item_info->item_type == ITEM_TEMP
|
<script type="text/javascript">
|
||||||
]) ?> <?= lang('Items.temp') ?>
|
$('#attributes').load('<?= "items/attributes/$item_info->item_id" ?>');
|
||||||
</label>
|
</script>
|
||||||
<?php } ?>
|
</div>
|
||||||
</div>
|
|
||||||
|
<label for="stock_type" class="form-label"><?= lang('Items.stock_type') ?><?= !empty($basic_version) ? '<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup>' : '' ?></label>
|
||||||
|
<div class="mb-3">
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
|
<input class="form-check-input" type="radio" name="stock_type" id="stock_type_stock" value="0" <?= $item_info->stock_type == HAS_STOCK ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
|
<label class="form-check-label" for="stock_type_stock"><?= lang('Items.stock') ?></label>
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="stock_type" id="stock_type_nonstock" value="1" <?= $item_info->stock_type == HAS_NO_STOCK ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Items.supplier'), 'supplier', ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="stock_type_nonstock"><?= lang('Items.nonstock') ?></label>
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_dropdown('supplier_id', $suppliers, $selected_supplier, ['class' => 'form-control']) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="item_type" class="form-label"><?= lang('Items.type') ?><?= !empty($basic_version) ? '<sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup>' : '' ?></label>
|
||||||
<?= form_label(lang('Items.cost_price'), 'cost_price', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="mb-3">
|
||||||
<div class="col-xs-4">
|
<div class="form-check form-check-inline">
|
||||||
<div class="input-group input-group-sm">
|
<input class="form-check-input" type="radio" name="item_type" id="item_type_standard" value="0" <?= $item_info->item_type == ITEM ? 'checked' : '' ?> <?= $standard_item_locked ? 'disabled readonly' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
<label class="form-check-label" for="item_type_standard"><?= lang('Items.standard') ?></label>
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'cost_price',
|
|
||||||
'id' => 'cost_price',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'onClick' => 'this.select();',
|
|
||||||
'value' => to_currency_no_money($item_info->cost_price)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="item_type" id="item_type_kit" value="1" <?= $item_info->item_type == ITEM_KIT ? 'checked' : '' ?> <?= $item_kit_disabled ? 'disabled readonly' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Items.unit_price'), 'unit_price', ['class' => 'required control-label col-xs-3']) ?>
|
<label class="form-check-label" for="item_type_kit"><?= lang('Items.kit') ?></label>
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?php if (!is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'unit_price',
|
|
||||||
'id' => 'unit_price',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'onClick' => 'this.select();',
|
|
||||||
'value' => to_currency_no_money($item_info->unit_price)
|
|
||||||
]) ?>
|
|
||||||
<?php if (is_right_side_currency_symbol()): ?>
|
|
||||||
<span class="input-group-addon input-sm"><b><?= esc($config['currency_symbol']) ?></b></span>
|
|
||||||
<?php endif; ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<?php if ($config['derive_sale_quantity'] == '1') { ?>
|
||||||
<?php if (!$use_destination_based_tax) { ?>
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="item_type" id="item_type_amount_entry" value="2" <?= $item_info->item_type == ITEM_AMOUNT_ENTRY ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Items.tax_1'), 'tax_percent_1', ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="item_type_amount_entry"><?= lang('Items.amount_entry') ?></label>
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_names[]',
|
|
||||||
'id' => 'tax_name_1',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_tax_info[0]['name'] ?? $config['default_tax_1_name']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_percents[]',
|
|
||||||
'id' => 'tax_percent_name_1',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => isset($item_tax_info[0]['percent']) ? to_tax_decimals($item_tax_info[0]['percent']) : to_tax_decimals($default_tax_1_rate)
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm"><b>%</b></span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.tax_2'), 'tax_percent_2', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_names[]',
|
|
||||||
'id' => 'tax_name_2',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_tax_info[1]['name'] ?? $config['default_tax_2_name']
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_percents[]',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'id' => 'tax_percent_name_2',
|
|
||||||
'value' => isset($item_tax_info[1]['percent']) ? to_tax_decimals($item_tax_info[1]['percent']) : to_tax_decimals($default_tax_2_rate)
|
|
||||||
]) ?>
|
|
||||||
<span class="input-group-addon input-sm"><b>%</b></span>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
<?php } ?>
|
<?php } ?>
|
||||||
|
<?php if ($allow_temp_item == 1) { ?>
|
||||||
<?php if ($use_destination_based_tax): ?>
|
<div class="form-check form-check-inline">
|
||||||
<div class="form-group form-group-sm">
|
<input class="form-check-input" type="radio" name="item_type" id="item_type_temp" value="3" <?= $item_info->item_type == ITEM_TEMP ? 'checked' : '' ?> <?= !empty($basic_version) ? 'required' : '' ?>>
|
||||||
<?= form_label(lang('Taxes.tax_category'), 'tax_category', ['class' => 'control-label col-xs-3']) ?>
|
<label class="form-check-label" for="item_type_temp"><?= lang('Items.temp') ?></label>
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'tax_category',
|
|
||||||
'id' => 'tax_category',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'size' => '50',
|
|
||||||
'value' => $tax_category
|
|
||||||
]) ?>
|
|
||||||
<?= form_hidden('tax_category_id', $tax_category_id) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<?php } ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="supplier_id" class="form-label"><?= lang('Items.supplier'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-truck"></i></span>
|
||||||
|
<select class="form-select" name="supplier_id" id="supplier_id">
|
||||||
|
<?php foreach ($suppliers as $key => $value) { ?>
|
||||||
|
<option value="<?= $key ?>" <?= $selected_supplier == $key ? 'selected' : '' ?>><?= $value ?></option>
|
||||||
|
<?php } ?>
|
||||||
|
</select>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="cost_price" class="form-label"><?= lang('Items.cost_price') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
|
<span class="input-group-text" id="cost_price-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
|
<input type="number" step="any" class="form-control" name="cost_price" id="cost_price" aria-describedby="cost_price-icon" value="<?= to_currency_no_money($item_info->cost_price) ?>" required>
|
||||||
<?php if ($include_hsn): ?>
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
<div class="form-group form-group-sm">
|
<span class="input-group-text" id="cost_price-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?= form_label(lang('Items.hsn_code'), 'category', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'hsn_code',
|
|
||||||
'id' => 'hsn_code',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $hsn_code
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php endif; ?>
|
<?php endif; ?>
|
||||||
|
</div>
|
||||||
|
|
||||||
<?php foreach ($stock_locations as $key => $location_detail) { ?>
|
<label for="unit_price" class="form-label"><?= lang('Items.unit_price') ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
<div class="form-group form-group-sm">
|
<div class="input-group mb-3">
|
||||||
<?= form_label(lang('Items.quantity') . ' ' . $location_detail['location_name'], "quantity_$key", ['class' => 'required control-label col-xs-3']) ?>
|
<?php if (!is_right_side_currency_symbol()): ?>
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="unit_price-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
<?= form_input([
|
<?php endif; ?>
|
||||||
'name' => "quantity_$key",
|
<input type="number" step="any" class="form-control" name="unit_price" id="unit_price" aria-describedby="unit_price-icon" value="<?= to_currency_no_money($item_info->unit_price) ?>" required>
|
||||||
'id' => "quantity_$key",
|
<?php if (is_right_side_currency_symbol()): ?>
|
||||||
'class' => 'required quantity form-control',
|
<span class="input-group-text" id="unit_price-icon"><?= esc($config['currency_symbol']) ?></span>
|
||||||
'onClick' => 'this.select();',
|
<?php endif; ?>
|
||||||
'value' => isset($item_info->item_id) ? to_quantity_decimals($location_detail['quantity']) : to_quantity_decimals(0)
|
</div>
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<?php if (!$use_destination_based_tax): ?>
|
||||||
<?= form_label(lang('Items.receiving_quantity'), 'receiving_quantity', ['class' => 'required control-label col-xs-3']) ?>
|
<label for="tax_name_1" class="form-label"><?= lang('Items.tax_1') ?></label>
|
||||||
<div class="col-xs-4">
|
<div class="input-group mb-3">
|
||||||
<?= form_input([
|
<span class="input-group-text" id="tax_name_1-icon"><i class="bi bi-piggy-bank"></i></span>
|
||||||
'name' => 'receiving_quantity',
|
<input type="text" class="form-control w-25" name="tax_names[]" id="tax_name_1" aria-describedby="tax_name_1-icon" value="<?= $item_tax_info[0]['name'] ?? $config['default_tax_1_name'] ?>">
|
||||||
'id' => 'receiving_quantity',
|
<input type="number" step="any" min="0" max="100" class="form-control" name="tax_percents[]" id="tax_percent_name_1" aria-describedby="tax_percent_name_1-icon" value="<?= isset($item_tax_info[0]['percent']) ? to_tax_decimals($item_tax_info[0]['percent']) : to_tax_decimals($default_tax_1_rate) ?>">
|
||||||
'class' => 'required form-control input-sm',
|
<span class="input-group-text" id="tax_percent_name_1-icon"><i class="bi bi-percent"></i></span>
|
||||||
'onClick' => 'this.select();',
|
|
||||||
'value' => isset($item_info->item_id) ? to_quantity_decimals($item_info->receiving_quantity) : to_quantity_decimals(0)
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="tax_name_2" class="form-label"><?= lang('Items.tax_2') ?></label>
|
||||||
<?= form_label(lang('Items.reorder_level'), 'reorder_level', ['class' => 'required control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-4">
|
<span class="input-group-text" id="tax_name_2-icon"><i class="bi bi-piggy-bank"></i></span>
|
||||||
<?= form_input([
|
<input type="text" class="form-control w-25" name="tax_names[]" id="tax_name_2" aria-describedby="tax_name_2-icon" value="<?= $item_tax_info[1]['name'] ?? $config['default_tax_2_name'] ?>">
|
||||||
'name' => 'reorder_level',
|
<input type="number" step="any" min="0" max="100" class="form-control" name="tax_percents[]" id="tax_percent_name_2" aria-describedby="tax_percent_name_2-icon" value="<?= isset($item_tax_info[1]['percent']) ? to_tax_decimals($item_tax_info[1]['percent']) : to_tax_decimals($default_tax_2_rate) ?>">
|
||||||
'id' => 'reorder_level',
|
<span class="input-group-text" id="tax_percent_name_2-icon"><i class="bi bi-percent"></i></span>
|
||||||
'class' => 'form-control input-sm',
|
</div>
|
||||||
'onClick' => 'this.select();',
|
<?php endif; ?>
|
||||||
'value' => isset($item_info->item_id) ? to_quantity_decimals($item_info->reorder_level) : to_quantity_decimals(0)
|
|
||||||
]) ?>
|
<?php if ($use_destination_based_tax): ?>
|
||||||
|
<label for="tax_category" class="form-label"><?= lang('Taxes.tax_category') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="tax_category-icon"><i class="bi bi-piggy-bank"></i></span>
|
||||||
|
<input type="hidden" name="tax_category_id" id="tax_category_id" value="<?= $tax_category_id ?>">
|
||||||
|
<input type="text" class="form-control" name="tax_category" id="tax_category" aria-describedby="tax_category-icon" value="<?= $tax_category ?>">
|
||||||
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
|
<?php if ($include_hsn): ?>
|
||||||
|
<label for="hsn_code" class="form-label"><?= lang('Items.hsn_code'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="hsn_code-icon"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="text" class="form-control" name="hsn_code" id="hsn_code" aria-describedby="hsn_code-icon" value="<?= $hsn_code ?>">
|
||||||
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
|
<?php foreach ($stock_locations as $key => $location_detail): ?>
|
||||||
|
<label for="quantity_<?= $key ?>" class="form-label"><?= lang('Items.quantity') . ' ' . $location_detail['location_name'] ?><sup><span class="badge text-primary"><i class="bi bi-asterisk"></i></span></sup></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="quantity_<?= $key ?>-icon"><i class="bi bi-boxes"></i></span>
|
||||||
|
<input type="text" class="form-control" name="quantity_<?= $key ?>" id="quantity_<?= $key ?>" aria-describedby="quantity_<?= $key ?>-icon" value="<?= isset($item_info->item_id) ? to_quantity_decimals($location_detail['quantity']) : to_quantity_decimals(0) ?>" required>
|
||||||
|
</div>
|
||||||
|
<?php endforeach; ?>
|
||||||
|
|
||||||
|
<label for="receiving_quantity" class="form-label"><?= lang('Items.receiving_quantity') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="receiving_quantity-icon"><i class="bi bi-truck"></i></span>
|
||||||
|
<input type="text" class="form-control" name="receiving_quantity" id="receiving_quantity" aria-describedby="receiving_quantity-icon" value="<?= isset($item_info->item_id) ? to_quantity_decimals($item_info->receiving_quantity) : to_quantity_decimals(0) ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="reorder_level" class="form-label"><?= lang('Items.reorder_level') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="reorder_level-icon"><i class="bi bi-list-ol"></i></span>
|
||||||
|
<input type="text" class="form-control" name="reorder_level" id="reorder_level" aria-describedby="reorder_level-icon" value="<?= isset($item_info->item_id) ? to_quantity_decimals($item_info->reorder_level) : to_quantity_decimals(0) ?>">
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="description" class="form-label"><?= lang('Items.description'); ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text"><i class="bi bi-chat"></i></span>
|
||||||
|
<textarea class="form-control" name="description" id="description" rows="6"><?= $item_info->description ?></textarea>
|
||||||
|
</div>
|
||||||
|
|
||||||
|
<label for="items_image" class="form-label"><?= lang('Items.image'); ?></label>
|
||||||
|
<div id="items_image" class="w-100 fileinput <?= $logo_exists ? 'fileinput-exists' : 'fileinput-new'; ?>" data-provides="fileinput">
|
||||||
|
<div class="input-group mb-3" aria-describedby="company-logo-desc">
|
||||||
|
<span class="input-group-text"><i class="bi bi-image"></i></span>
|
||||||
|
<div class="fileinput-new form-control rounded-end mb-0" style="height: 200px; cursor: default;"></div>
|
||||||
|
<div class="fileinput-exists fileinput-preview img-thumbnail form-control rounded-end mb-0 bg-light mh-100" style="height: 200px; cursor: default; background-size: 40px 40px; background-position: 0 0, 20px 20px; background-image: linear-gradient(45deg, white 25%, transparent 25%, transparent 75%, white 75%, white), linear-gradient(45deg, white 25%, transparent 25%, transparent 75%, white 75%, white);">
|
||||||
|
<img class="mh-100 mw-100" data-src="holder.js/100%x100%" alt="<?= esc(lang('Config.company_logo')) ?>" src="<?= $image_path ?>">
|
||||||
</div>
|
</div>
|
||||||
</div>
|
</div>
|
||||||
|
<div type="button" class="btn btn-secondary btn-file me-2">
|
||||||
|
<span class="fileinput-new"><i class="bi bi-hand-index me-2"></i><?= lang('Items.select_image') ?></span>
|
||||||
|
<span class="fileinput-exists"><i class="bi bi-images me-2"></i><?= lang('Items.change_image') ?></span>
|
||||||
|
<input type="file" name="items_image" accept="image/*">
|
||||||
|
</div>
|
||||||
|
<a type="button" class="btn btn-outline-secondary fileinput-exists" data-dismiss="fileinput">
|
||||||
|
<i class="bi bi-eraser me-2"></i><?= lang('Items.remove_image') ?>
|
||||||
|
</a>
|
||||||
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="form-check mb-3">
|
||||||
<?= form_label(lang('Items.description'), 'description', ['class' => 'control-label col-xs-3']) ?>
|
<input class="form-check-input" type="checkbox" name="allow_alt_description" id="allow_alt_description" value="1" <?= $item_info->allow_alt_description == 1 ? 'checked' : '' ?>>
|
||||||
<div class="col-xs-8">
|
<label class="form-check-label" for="allow_alt_description"><?= lang('Items.allow_alt_description') ?></label>
|
||||||
<?= form_textarea([
|
</div>
|
||||||
'name' => 'description',
|
|
||||||
'id' => 'description',
|
<div class="form-check mb-3">
|
||||||
'class' => 'form-control input-sm',
|
<input class="form-check-input" type="checkbox" name="is_serialized" id="is_serialized" value="1" <?= $item_info->is_serialized == 1 ? 'checked' : '' ?>>
|
||||||
'value' => $item_info->description
|
<label class="form-check-label" for="is_serialized"><?= lang('Items.is_serialized') ?></label>
|
||||||
]) ?>
|
</div>
|
||||||
</div>
|
|
||||||
|
<?php if ($config['multi_pack_enabled'] == '1'): ?>
|
||||||
|
<label for="qty_per_pack" class="form-label"><?= lang('Items.qty_per_pack') ?></label>
|
||||||
|
<div class="input-group mb-3">
|
||||||
|
<span class="input-group-text" id="qty_per_pack-icon"><i class="bi bi-123"></i></span>
|
||||||
|
<input type="text" class="form-control" name="qty_per_pack" id="qty_per_pack" aria-describedby="qty_per_pack-icon" value="<?= isset($item_info->item_id) ? to_quantity_decimals($item_info->qty_per_pack) : to_quantity_decimals(0) ?>">
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="pack_name" class="form-label"><?= lang('Items.pack_name') ?></label>
|
||||||
<?= form_label(lang('Items.image'), 'items_image', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-8">
|
<span class="input-group-text" id="pack_name-icon"><i class="bi bi-box2-heart"></i></span>
|
||||||
<div class="fileinput <?= $logo_exists ? 'fileinput-exists' : 'fileinput-new' ?>" data-provides="fileinput">
|
<input type="text" class="form-control" name="pack_name" id="pack_name" aria-describedby="pack_name-icon" value="<?= $item_info->pack_name ?>">
|
||||||
<div class="fileinput-new thumbnail" style="width: 100px; height: 100px;"></div>
|
|
||||||
<div class="fileinput-preview fileinput-exists thumbnail" style="max-width: 100px; max-height: 100px;">
|
|
||||||
<img data-src="holder.js/100%x100%" alt="<?= lang('Items.image') ?>"
|
|
||||||
src="<?= $image_path ?>"
|
|
||||||
style="max-height: 100%; max-width: 100%;">
|
|
||||||
</div>
|
|
||||||
<div>
|
|
||||||
<span class="btn btn-default btn-sm btn-file">
|
|
||||||
<span class="fileinput-new"><?= lang('Items.select_image') ?></span>
|
|
||||||
<span class="fileinput-exists"><?= lang('Items.change_image') ?></span>
|
|
||||||
<input type="file" name="items_image" accept="image/*">
|
|
||||||
</span>
|
|
||||||
<a href="#" class="btn btn-default btn-sm fileinput-exists" data-dismiss="fileinput"><?= lang('Items.remove_image') ?></a>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<label for="low_sell_item_name" class="form-label"><?= lang('Items.low_sell_item') ?></label>
|
||||||
<?= form_label(lang('Items.allow_alt_description'), 'allow_alt_description', ['class' => 'control-label col-xs-3']) ?>
|
<div class="input-group mb-3">
|
||||||
<div class="col-xs-1">
|
<span class="input-group-text" id="pack_name-icon"><i class="bi bi-thermometer-low"></i></span>
|
||||||
<?= form_checkbox([
|
<input type="hidden" name="low_sell_item_id" value="<?= $selected_low_sell_item_id ?>">
|
||||||
'name' => 'allow_alt_description',
|
<input type="text" class="form-control" name="low_sell_item_name" id="low_sell_item_name" aria-describedby="low_sell_item_name-icon" value="<?= $selected_low_sell_item ?>">
|
||||||
'id' => 'allow_alt_description',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_info->allow_alt_description == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
</div>
|
||||||
|
<?php endif; ?>
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
<div class="form-check mb-3">
|
||||||
<?= form_label(lang('Items.is_serialized'), 'is_serialized', ['class' => 'control-label col-xs-3']) ?>
|
<input class="form-check-input" type="checkbox" name="is_deleted" id="is_deleted" value="1" <?= $item_info->deleted == 1 ? 'checked' : '' ?>>
|
||||||
<div class="col-xs-1">
|
<label class="form-check-label text-danger" for="is_deleted"><?= lang('Items.is_deleted') ?></label>
|
||||||
<?= form_checkbox([
|
</div>
|
||||||
'name' => 'is_serialized',
|
|
||||||
'id' => 'is_serialized',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_info->is_serialized == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
<?php if ($config['multi_pack_enabled'] == '1') { ?>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.qty_per_pack'), 'qty_per_pack', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-4">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'qty_per_pack',
|
|
||||||
'id' => 'qty_per_pack',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => isset($item_info->item_id) ? to_quantity_decimals($item_info->qty_per_pack) : to_quantity_decimals(0)
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.pack_name'), 'name', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'pack_name',
|
|
||||||
'id' => 'pack_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $item_info->pack_name
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.low_sell_item'), 'low_sell_item_name', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-8">
|
|
||||||
<div class="input-group input-group-sm">
|
|
||||||
<?= form_input([
|
|
||||||
'name' => 'low_sell_item_name',
|
|
||||||
'id' => 'low_sell_item_name',
|
|
||||||
'class' => 'form-control input-sm',
|
|
||||||
'value' => $selected_low_sell_item
|
|
||||||
]) ?>
|
|
||||||
<?= form_hidden('low_sell_item_id', $selected_low_sell_item_id) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
<?php } ?>
|
|
||||||
|
|
||||||
<div class="form-group form-group-sm">
|
|
||||||
<?= form_label(lang('Items.is_deleted'), 'is_deleted', ['class' => 'control-label col-xs-3']) ?>
|
|
||||||
<div class="col-xs-1">
|
|
||||||
<?= form_checkbox([
|
|
||||||
'name' => 'is_deleted',
|
|
||||||
'id' => 'is_deleted',
|
|
||||||
'value' => 1,
|
|
||||||
'checked' => $item_info->deleted == 1
|
|
||||||
]) ?>
|
|
||||||
</div>
|
|
||||||
</div>
|
|
||||||
|
|
||||||
</fieldset>
|
|
||||||
<?= form_close() ?>
|
<?= form_close() ?>
|
||||||
|
|
||||||
<script type="text/javascript">
|
<script type="text/javascript">
|
||||||
|
|||||||
Some files were not shown because too many files have changed in this diff Show More
Reference in New Issue
Block a user