Conditions.vue 8.7 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196197198199200201202203204205206207208209210211212213214215216217218219220221222223224225226227228229230231232233234235236237238239240241242243244245246247248249250251252253254255256257258259260261262263264265266267268269270271272273274275276277278279280281282283284285286287288289290291292293294295296297298299300301302303304305306307308309310311312313314315316317318319320321322323324325326327328329330331332333
  1. <template>
  2. <div class="props">
  3. <div v-if="data.conditions && data.conditions.length > 0" class="form-item banner">
  4. <label>{{$t('触发条件')}}</label>
  5. <div class="w-full flex middle between">
  6. <div></div>
  7. <t-radio-group class="ml-8" v-model="data.conditionType">
  8. <t-radio value="and"> {{$t('满足全部条件')}} </t-radio>
  9. <t-radio value="or"> {{$t('满足任意条件')}} </t-radio>
  10. </t-radio-group>
  11. </div>
  12. </div>
  13. <div v-for="(c, index) in data.conditions" class="mb-12">
  14. <div class="flex middle between head">
  15. <div class="flex middle">
  16. <arrow-right-icon class="mr-4" />
  17. <!-- <t-icon name="arrow-right" class="mr-4" /> -->
  18. {{$t(' 条件')}}{{ index + 1 }}
  19. </div>
  20. <close-icon class="hover"
  21. @click="data.conditions.splice(index, 1)"/>
  22. <!-- <t-icon
  23. name="close"
  24. class="hover"
  25. @click="data.conditions.splice(index, 1)"
  26. /> -->
  27. </div>
  28. <div class="">
  29. <div class="form-item mt-4">
  30. <label>{{$t('条件类型')}}</label>
  31. <t-radio-group class="ml-8" v-model="c.type">
  32. <t-radio value> {{$t('关系条件')}} </t-radio>
  33. <t-radio value="fn"> {{$t('高级条件')}} </t-radio>
  34. </t-radio-group>
  35. </div>
  36. <template v-if="!c.type">
  37. <div class="form-item mt-8">
  38. <label>{{$t( '属性名' )}}</label>
  39. <t-select-input
  40. v-model:inputValue="c.key"
  41. :value="c.keyLabel"
  42. v-model:popupVisible="c.keyPopupVisible"
  43. allow-input
  44. clearable
  45. @clear="c.keyLabel = undefined"
  46. @focus="c.keyPopupVisible = true"
  47. @blur="c.keyPopupVisible = false"
  48. @input-change="onKeyInput(c)"
  49. class="shrink-0"
  50. style="width: 152px"
  51. >
  52. <template #panel>
  53. <ul style="padding: 8px 12px">
  54. <li
  55. v-for="item in cprops"
  56. :key="item.value"
  57. @click="
  58. c.key = item.value;
  59. c.keyLabel = item.label;
  60. c.keyPopupVisible = false;
  61. "
  62. >
  63. {{ item.label }}
  64. </li>
  65. </ul>
  66. </template>
  67. </t-select-input>
  68. </div>
  69. <div class="form-item mt-8">
  70. <label>{{$t('关系运算')}}</label>
  71. <t-select v-model="c.operator" :options="operatorOptions" clearable class="shrink-0" :placeholder="$t('关系运算')"></t-select>
  72. </div>
  73. <div class="form-item mt-8">
  74. <label>{{$t('运算对象')}}</label>
  75. <t-select v-model="c.valueType" class="shrink-0" :placeholder="$t('固定值')">
  76. <t-option key value :label="$t('固定值')"> {{$t('固定值')}} </t-option>
  77. <t-option key="prop" value="prop" :label="$t('对象属性值')">
  78. {{$t('对象属性值')}}
  79. </t-option>
  80. </t-select>
  81. </div>
  82. <div v-if="!c.valueType" class="form-item mt-8 form-item-valueType">
  83. <label>{{$t( '值' )}}</label>
  84. <t-input v-model="c.value" @change="valueChange($event,c)" class="shrink-0" style="width: 320px" />
  85. </div>
  86. <template v-else>
  87. <div class="form-item mt-8">
  88. <label>{{$t('对象')}}</label>
  89. <t-tree-select v-model="c.target" :data="penTree" filterable class="shrink-0" @change="onChangeTriggerTarget(c)" :placeholder="$t('对象')"></t-tree-select>
  90. </div>
  91. <div class="form-item mt-8">
  92. <label>{{$t( '属性' )}}</label>
  93. <t-select-input
  94. v-model:inputValue="c.value"
  95. :value="c.label"
  96. v-model:popupVisible="c.popupVisible"
  97. allow-input
  98. clearable
  99. @clear="c.label = undefined"
  100. @focus="c.popupVisible = true"
  101. @blur="c.popupVisible = false"
  102. @input-change="onInput(c)"
  103. class="shrink-0"
  104. >
  105. <template #panel>
  106. <ul style="padding: 8px 12px">
  107. <li
  108. v-for="item in cprops"
  109. :key="item.value"
  110. @click="
  111. c.value = item.value;
  112. c.label = item.label;
  113. c.popupVisible = false;
  114. "
  115. >
  116. {{ item.label }}
  117. </li>
  118. </ul>
  119. </template>
  120. </t-select-input>
  121. </div>
  122. </template>
  123. </template>
  124. <template v-else>
  125. <div>function condition(pen) {</div>
  126. <CodeEditor class="mt-4" @change="codeChange($event,c)" v-model="c.fnJs" />
  127. <div class="mt-4">}</div>
  128. </template>
  129. </div>
  130. </div>
  131. <div class="mt-8 mb-8">
  132. <a @click="addTriggerCondition(data)"> + {{$t('添加触发条件')}} </a>
  133. </div>
  134. </div>
  135. </template>
  136. <script lang="ts" setup>
  137. import { onBeforeMount, ref, getCurrentInstance } from 'vue';
  138. import CodeEditor from '@/views/components/common/CodeEditor.vue';
  139. import { getPenTree, typeOptions, changeType} from '@/services/common';
  140. import {ArrowRightIcon,CloseIcon} from 'tdesign-icons-vue-next';
  141. const { proxy } = getCurrentInstance();
  142. const $t = proxy.$t
  143. const penTree: any = ref([]);
  144. const { data } = defineProps<{
  145. data: any;
  146. }>();
  147. onBeforeMount(() => {
  148. if (!data.conditions) {
  149. data.conditions = [];
  150. }
  151. penTree.value = getPenTree();
  152. });
  153. const onChangeTriggerTarget = (c: any) => {
  154. // c.targetProps = [
  155. // {
  156. // value: 'x',
  157. // label: 'X',
  158. // },
  159. // {
  160. // value: 'y',
  161. // label: 'Y',
  162. // },
  163. // {
  164. // value: 'width',
  165. // label: $t('宽'),
  166. // },
  167. // {
  168. // value: 'height',
  169. // label: $t('高'),
  170. // },
  171. // {
  172. // value: 'visible',
  173. // label: $t('显示'),
  174. // },
  175. // {
  176. // value: 'text',
  177. // label: $t('文字'),
  178. // },
  179. // {
  180. // value: 'progress',
  181. // label: $t('进度'),
  182. // },
  183. // {
  184. // value: 'showChild',
  185. // label: $t('状态'),
  186. // },
  187. // {
  188. // value: 'rotate',
  189. // label: $t('旋转'),
  190. // },
  191. // ];
  192. const target: any = meta2d.findOne(c.target);
  193. if (target && target.realTimes) {
  194. for (const item of target.realTimes) {
  195. const found = cprops.value.findIndex((elem: any) => elem.value === item.key);
  196. if (found < 0) {
  197. cprops.value.push({
  198. value: item.key,
  199. label: item.label,
  200. });
  201. }
  202. }
  203. }
  204. };
  205. const addTriggerCondition = (data: any) => {
  206. if (!data.conditionType) {
  207. data.conditionType = 'and';
  208. }
  209. data.conditions.push({
  210. type: '',
  211. operator: '=',
  212. valueType: '',
  213. });
  214. };
  215. const onKeyInput = (item: any) => {
  216. item.keyLabel = item.key;
  217. };
  218. const onInput = (item: any) => {
  219. item.label = item.value;
  220. };
  221. const cprops = ref<any>([
  222. {
  223. value: 'x',
  224. label: 'X',
  225. },
  226. {
  227. value: 'y',
  228. label: 'Y',
  229. },
  230. {
  231. value: 'width',
  232. label: $t('宽'),
  233. },
  234. {
  235. value: 'height',
  236. label: $t('高'),
  237. },
  238. {
  239. value: 'visible',
  240. label: $t('显示'),
  241. },
  242. {
  243. value: 'text',
  244. label: $t('文字'),
  245. },
  246. {
  247. value: 'color',
  248. label: $t('颜色'),
  249. },
  250. {
  251. value: 'background',
  252. label: $t('背景颜色'),
  253. },
  254. {
  255. value: 'progress',
  256. label: $t('进度'),
  257. },
  258. {
  259. value: 'progressColor',
  260. label: $t('进度颜色'),
  261. },
  262. {
  263. value: 'showChild',
  264. label: $t('状态'),
  265. },
  266. {
  267. value: 'rotate',
  268. label: $t('旋转'),
  269. },
  270. {
  271. value: 'disabled',
  272. label: $t('禁用'),
  273. },
  274. {
  275. value: 'selectedKey',
  276. label: $t('单选选中值'),
  277. },
  278. {
  279. value: 'animateReverse',
  280. label: $t('连线动画反向'),
  281. }
  282. ]);
  283. const operatorOptions = [
  284. { label: '=', value: '=' },
  285. { label: '!=', value: '!=' },
  286. { label: '>', value: '>' },
  287. { label: '<', value: '<' },
  288. { label: '>=', value: '>=' },
  289. { label: '<=', value: '<=' },
  290. { label: $t('包含'), value: '[)' },
  291. { label: $t('不包含'), value: '![)' },
  292. ];
  293. const valueChange = (e,c:any)=>{
  294. c.value= changeType(e);
  295. }
  296. const codeChange = (e:any,a:any)=>{
  297. a.fn = null;
  298. }
  299. </script>
  300. <style lang="postcss" scoped>
  301. .props {
  302. .form-item {
  303. :deep(.t-radio-group .t-radio) {
  304. margin-right: 10px;
  305. .t-radio__label {
  306. margin-left: 4px;
  307. }
  308. }
  309. }
  310. .form-item-valueType {
  311. /* :deep(.t-input) {
  312. padding: 0px;
  313. } */
  314. }
  315. .banner {
  316. /* background-color: var(--color-background-input); */
  317. /* padding: 0 12px; */
  318. }
  319. }
  320. </style>