Widget Dialog
This commit is contained in:
parent
cafd4d9184
commit
e4ea0171fa
2 changed files with 209 additions and 64 deletions
|
|
@ -821,6 +821,54 @@ public class ListFormSeeder_Administration : IDataSeedContributor, ITransientDep
|
|||
}),
|
||||
FormFieldsDefaultValueJson = JsonSerializer.Serialize(new FieldsDefaultValue[] {
|
||||
new FieldsDefaultValue() { FieldName = "IsActive", FieldDbType = DbType.Boolean, Value = "true", CustomValueType = FieldCustomValueTypeEnum.Value }
|
||||
}),
|
||||
WidgetsJson = JsonSerializer.Serialize(new List<WidgetEditDto>
|
||||
{
|
||||
new()
|
||||
{
|
||||
ColGap = 3,
|
||||
ColSpan = 4,
|
||||
SqlQuery = @"
|
||||
SELECT
|
||||
'Aktif' AS ""Title"",
|
||||
COUNT(""Id"") AS ""Value"",
|
||||
'blue' AS ""Color"",
|
||||
'Aktif Kullanıcılar' AS ""SubTitle"",
|
||||
'FaUserCheck' AS ""Icon""
|
||||
FROM ""AbpUsers""
|
||||
WHERE ""IsActive"" = 'true'
|
||||
|
||||
UNION ALL
|
||||
|
||||
SELECT
|
||||
'Pasif' AS ""Title"",
|
||||
COUNT(""Id"") AS ""Value"",
|
||||
'green' AS ""Color"",
|
||||
'Pasif Kullanıcılar' AS ""SubTitle"",
|
||||
'FaUserSlash' AS ""Icon""
|
||||
FROM ""AbpUsers""
|
||||
WHERE ""IsActive"" = 'false'
|
||||
|
||||
UNION ALL
|
||||
|
||||
SELECT
|
||||
'Doğrulama' AS ""Title"",
|
||||
COUNT(""Id"") AS ""Value"",
|
||||
'purple' AS ""Color"",
|
||||
'Yönetici Doğrulaması bekleyenler' AS ""SubTitle"",
|
||||
'FaUserClock' AS ""Icon""
|
||||
FROM ""AbpUsers""
|
||||
WHERE ""IsVerified"" = 'false';
|
||||
",
|
||||
Title = "Title",
|
||||
Value = "Value",
|
||||
ValueClassName = "bg-5 text-sm",
|
||||
Color = "Color",
|
||||
Icon = "Icon",
|
||||
SubTitle = "SubTitle",
|
||||
ClassName = "mb-3",
|
||||
IsActive = true
|
||||
}
|
||||
})
|
||||
});
|
||||
|
||||
|
|
|
|||
|
|
@ -10,6 +10,7 @@ import {
|
|||
toast,
|
||||
Tooltip,
|
||||
} from '@/components/ui'
|
||||
import SqlEditor from '@/views/sqlQueryManager/components/SqlEditor'
|
||||
import { ListFormJsonRowDto } from '@/proxy/admin/list-form/models'
|
||||
import { SelectBoxOption } from '@/types/shared'
|
||||
import { useStoreActions, useStoreState } from '@/store'
|
||||
|
|
@ -89,16 +90,17 @@ function JsonRowOpDialogWidget({
|
|||
data.widgetValues ?? {
|
||||
colGap: 3,
|
||||
colSpan: 3,
|
||||
sqlQuery: '',
|
||||
sqlQuery:
|
||||
"SELECT 'Total Records' as title, COUNT(*) as value, 'blue' as color, 'FaChartBar' as icon, 'Active records' as subTitle FROM YourTable WHERE IsActive = 1",
|
||||
className: 'mb-3',
|
||||
valueClassName: 'bg-5 text-sm',
|
||||
title: 'Title',
|
||||
value: 'Value',
|
||||
color: 'Color',
|
||||
icon: 'Icon',
|
||||
subTitle: 'SubTitle',
|
||||
title: 'title',
|
||||
value: 'value',
|
||||
color: 'color',
|
||||
icon: 'icon',
|
||||
subTitle: 'subTitle',
|
||||
onClick: '',
|
||||
isActive: false,
|
||||
isActive: true,
|
||||
}
|
||||
}
|
||||
validationSchema={schema}
|
||||
|
|
@ -135,11 +137,11 @@ function JsonRowOpDialogWidget({
|
|||
}
|
||||
}}
|
||||
>
|
||||
{({ touched, errors, values, isSubmitting }) => (
|
||||
{({ touched, errors, values, isSubmitting, setFieldValue }) => (
|
||||
<Form>
|
||||
<FormContainer size="sm">
|
||||
<div className="h-full overflow-y-auto p-2">
|
||||
<div className="grid grid-cols-3 gap-4">
|
||||
<div className="h-full overflow-y-auto p-1">
|
||||
<div className="grid grid-cols-5 gap-4">
|
||||
<FormItem
|
||||
label="Column Gap (Sütun Boşluğu)"
|
||||
invalid={errors.colGap && touched.colGap}
|
||||
|
|
@ -175,6 +177,52 @@ function JsonRowOpDialogWidget({
|
|||
</Field>
|
||||
</FormItem>
|
||||
|
||||
<Tooltip
|
||||
title={
|
||||
<div className="text-xs">
|
||||
<div className="font-semibold mb-1">Widget Container CSS Classes</div>
|
||||
<div>Examples: mb-3, mt-2, p-4, rounded-lg, shadow-md</div>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
<FormItem
|
||||
label="Class Name"
|
||||
invalid={errors.className && touched.className}
|
||||
errorMessage={errors.className}
|
||||
>
|
||||
<Field
|
||||
type="text"
|
||||
autoComplete="off"
|
||||
name="className"
|
||||
placeholder="Tailwind CSS classes: mb-3, mt-2, p-4..."
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
</Tooltip>
|
||||
|
||||
<Tooltip
|
||||
title={
|
||||
<div className="text-xs">
|
||||
<div className="font-semibold mb-1">Value Display CSS Classes</div>
|
||||
<div>Examples: text-3xl, text-2xl, font-bold, text-sm, text-center</div>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
<FormItem
|
||||
label="Value Class Name"
|
||||
invalid={errors.valueClassName && touched.valueClassName}
|
||||
errorMessage={errors.valueClassName}
|
||||
>
|
||||
<Field
|
||||
type="text"
|
||||
autoComplete="off"
|
||||
name="valueClassName"
|
||||
placeholder="Tailwind CSS classes: text-3xl, font-bold..."
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
</Tooltip>
|
||||
|
||||
<FormItem
|
||||
label="IsActive"
|
||||
invalid={errors.isActive && touched.isActive}
|
||||
|
|
@ -189,25 +237,46 @@ function JsonRowOpDialogWidget({
|
|||
</FormItem>
|
||||
</div>
|
||||
|
||||
<Tooltip
|
||||
title={
|
||||
<div className="text-xs max-h-96 overflow-y-auto">
|
||||
<div className="font-semibold mb-2">SQL Query Examples:</div>
|
||||
<div className="space-y-3">
|
||||
<div>
|
||||
<code className="text-xs bg-gray-800 p-1 rounded block mt-1">
|
||||
SELECT 'Aktif' as title, COUNT(Id) as value,
|
||||
<br />
|
||||
'blue' as color, 'FaChartBar' as icon,
|
||||
<br />
|
||||
'Aktif kayıtlar' as subTitle
|
||||
<br />
|
||||
FROM YourTable WHERE IsActive = 1
|
||||
</code>
|
||||
</div>
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
Sql Query
|
||||
</Tooltip>
|
||||
|
||||
<FormItem
|
||||
label="Sql Query"
|
||||
invalid={errors.sqlQuery && touched.sqlQuery}
|
||||
errorMessage={errors.sqlQuery}
|
||||
>
|
||||
<Field
|
||||
type="text"
|
||||
autoComplete="off"
|
||||
name="sqlQuery"
|
||||
placeholder="Sql Query"
|
||||
component={Input}
|
||||
textArea={true}
|
||||
<div
|
||||
className="border rounded-lg overflow-hidden"
|
||||
style={{ height: '200px' }}
|
||||
>
|
||||
<SqlEditor
|
||||
value={values.sqlQuery || ''}
|
||||
onChange={(value) => setFieldValue('sqlQuery', value || '')}
|
||||
height="200px"
|
||||
/>
|
||||
</div>
|
||||
</FormItem>
|
||||
|
||||
<div className="bg-gray-100 p-1 rounded-md pb-2">
|
||||
<span className="text-gray-500 font-bold">SQL Query Fields</span>
|
||||
</div>
|
||||
<div className="grid grid-cols-6 gap-2">
|
||||
<div className="grid grid-cols-5 gap-2">
|
||||
<FormItem
|
||||
label="Title Field"
|
||||
invalid={errors.title && touched.title}
|
||||
|
|
@ -217,7 +286,7 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="title"
|
||||
placeholder="Title Field"
|
||||
placeholder="Column name from SQL query e.g., 'title'"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
|
|
@ -231,12 +300,30 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="value"
|
||||
placeholder="Value Field"
|
||||
placeholder="Column name from SQL query e.g., 'value'"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
|
||||
<Tooltip title={'blue, green, purple, gray, red, yellow, pink, indigo, teal'}>
|
||||
<Tooltip
|
||||
title={
|
||||
<div className="text-xs">
|
||||
<div className="font-semibold mb-1">Available Colors:</div>
|
||||
<div className="grid grid-cols-2 gap-1">
|
||||
<div>• blue</div>
|
||||
<div>• green</div>
|
||||
<div>• purple</div>
|
||||
<div>• gray</div>
|
||||
<div>• red</div>
|
||||
<div>• yellow</div>
|
||||
<div>• pink</div>
|
||||
<div>• indigo</div>
|
||||
<div>• teal</div>
|
||||
<div>• orange</div>
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
<FormItem
|
||||
label="Color Field"
|
||||
invalid={errors.color && touched.color}
|
||||
|
|
@ -246,7 +333,7 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="color"
|
||||
placeholder="Color"
|
||||
placeholder="blue, green, purple, gray, red..."
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
|
|
@ -254,7 +341,45 @@ function JsonRowOpDialogWidget({
|
|||
|
||||
<Tooltip
|
||||
title={
|
||||
'FaHome, FaUser, FaSearch, FaCog, FaBell etc. (react-icons/fa icons)'
|
||||
<div className="text-xs max-h-64 overflow-y-auto">
|
||||
<div className="font-semibold mb-2">Popular Icon Examples:</div>
|
||||
<div className="space-y-1">
|
||||
<div>
|
||||
📊 <strong>Charts:</strong> FaChartBar, FaChartLine, FaChartPie,
|
||||
FaChartArea
|
||||
</div>
|
||||
<div>
|
||||
💰 <strong>Finance:</strong> FaDollarSign, FaMoneyBill, FaWallet,
|
||||
FaCreditCard
|
||||
</div>
|
||||
<div>
|
||||
👥 <strong>Users:</strong> FaUser, FaUsers, FaUserCircle, FaUserTie
|
||||
</div>
|
||||
<div>
|
||||
📦 <strong>Business:</strong> FaShoppingCart, FaBoxes, FaWarehouse,
|
||||
FaTruck
|
||||
</div>
|
||||
<div>
|
||||
📈 <strong>Analytics:</strong> FaArrowUp, FaArrowDown,
|
||||
FaArrowTrendUp
|
||||
</div>
|
||||
<div>
|
||||
⚙️ <strong>Settings:</strong> FaCog, FaTools, FaWrench
|
||||
</div>
|
||||
<div>
|
||||
🔔 <strong>Alerts:</strong> FaBell, FaExclamation, FaInfoCircle
|
||||
</div>
|
||||
<div>
|
||||
📁 <strong>Files:</strong> FaFile, FaFolder, FaFileAlt, FaDownload
|
||||
</div>
|
||||
<div>
|
||||
🏠 <strong>Other:</strong> FaHome, FaBuilding, FaGlobe, FaHeart
|
||||
</div>
|
||||
</div>
|
||||
<div className="mt-2 pt-2 border-t">
|
||||
All icons from <strong>react-icons/fa</strong> (Font Awesome)
|
||||
</div>
|
||||
</div>
|
||||
}
|
||||
>
|
||||
<FormItem
|
||||
|
|
@ -266,7 +391,7 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="icon"
|
||||
placeholder="Icon"
|
||||
placeholder="FaChartBar, FaUsers, FaShoppingCart..."
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
|
|
@ -281,10 +406,11 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="subTitle"
|
||||
placeholder="Sub Title"
|
||||
placeholder="Column name from SQL query e.g., 'subTitle'"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
</div>
|
||||
|
||||
<FormItem
|
||||
label="On Click"
|
||||
|
|
@ -295,41 +421,12 @@ function JsonRowOpDialogWidget({
|
|||
type="text"
|
||||
autoComplete="off"
|
||||
name="onClick"
|
||||
placeholder="On Click"
|
||||
placeholder="JavaScript function: () => alert('Clicked')"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
</div>
|
||||
|
||||
<FormItem
|
||||
label="Class Name"
|
||||
invalid={errors.className && touched.className}
|
||||
errorMessage={errors.className}
|
||||
>
|
||||
<Field
|
||||
type="text"
|
||||
autoComplete="off"
|
||||
name="className"
|
||||
placeholder="Class Name"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
|
||||
<FormItem
|
||||
label="Value Class Name"
|
||||
invalid={errors.valueClassName && touched.valueClassName}
|
||||
errorMessage={errors.valueClassName}
|
||||
>
|
||||
<Field
|
||||
type="text"
|
||||
autoComplete="off"
|
||||
name="valueClassName"
|
||||
placeholder="Value Class Name"
|
||||
component={Input}
|
||||
/>
|
||||
</FormItem>
|
||||
</div>
|
||||
<div className="text-right mt-4">
|
||||
<div className="text-right mt-2">
|
||||
<Button className="ltr:mr-2 rtl:ml-2" variant="plain" onClick={handleClose}>
|
||||
Cancel
|
||||
</Button>
|
||||
|
|
|
|||
Loading…
Reference in a new issue