This commit is contained in:
Qwreey 2023-02-16 20:57:00 +09:00
parent a181e93ff2
commit 9f2872e53e
7 changed files with 257 additions and 31 deletions

View file

@ -2,6 +2,7 @@ local module = {};
local pack = table.pack; local pack = table.pack;
local match = string.match; local match = string.match;
local insert = table.insert; local insert = table.insert;
local gsub = string.gsub
---@param shared quad_export ---@param shared quad_export
---@return quad_module_class ---@return quad_module_class
@ -59,6 +60,7 @@ function module.init(shared)
end end
return item[index]; return item[index];
end end
new.getProperty = getProperty
local function setProperty(item,index,value,ClassName) local function setProperty(item,index,value,ClassName)
if type(item) == "table" then item[index] = value; return; end if type(item) == "table" then item[index] = value; return; end
@ -92,12 +94,13 @@ function module.init(shared)
item[index] = value; -- set property item[index] = value; -- set property
end end
end end
new.setProperty = setProperty
local function rawGetProperty(item,index) local function rawGetProperty(item,index)
return item[index]; return item[index];
end end
local function pcallGetProperty(item,index) local function pcallGetProperty(item,index)
local ok,err = pcall(rawGetProperty,index); local ok,err = pcall(rawGetProperty,item,index);
if ok then return err; end if ok then return err; end
return nil; return nil;
end end
@ -109,7 +112,8 @@ function module.init(shared)
local indexType = typeof(index); local indexType = typeof(index);
-- child -- child
if indexType == "string" and valueType == "table" and pcallGetProperty(value,"__type") == "quad_register" then -- register (bind to store event) local quadType = valueType == "table" and pcallGetProperty(value,"__type")
if indexType == "string" and valueType == "table" and quadType == "quad_register" then -- register (bind to store event)
processedProperty[index] = true; -- ignore next processedProperty[index] = true; -- ignore next
-- store reading -- store reading
do do
@ -155,7 +159,7 @@ function module.init(shared)
processedProperty[index] = true; -- ignore next processedProperty[index] = true; -- ignore next
-- prop set -- prop set
setProperty(item,index,value,className); setProperty(item,index,value,className);
elseif indexType == "number" and valueType == "table" and pcallGetProperty(value,"__type") == "quad_style" then -- style elseif indexType == "number" and valueType == "table" and quadType == "quad_style" then -- style
-- style parsing -- style parsing
for _,thisStyle in ipairs(parseStyles(value)) do for _,thisStyle in ipairs(parseStyles(value)) do
if not processedProperty[thisStyle] then if not processedProperty[thisStyle] then
@ -253,7 +257,7 @@ function module.init(shared)
local lastName = prop; local lastName = prop;
return function (nprop,...) return function (nprop,...)
nprop = nprop or {}; nprop = nprop or {};
nprop.Name = lastName; nprop.Name = gsub(gsub(match(lastName,"[^,]+")," +$",""),"^ +","");
for styleName,styleObj in pairs(styleList) do for styleName,styleObj in pairs(styleList) do
if match(prop,styleName) then if match(prop,styleName) then
insert(nprop,styleObj); insert(nprop,styleObj);
@ -288,7 +292,7 @@ function module.init(shared)
-- make metatable -- make metatable
prop = storeNew(prop,nil); prop = storeNew(prop,nil);
local parent = prop and (prop.Parent or prop.parent); local parent = prop and (prop.Parent or prop.parent);
local self = {__prop = prop; __parent = parent}; local self = {__prop = prop; __parent = parent,__propertyChangedSignals = {}};
local init = this.init; local init = this.init;
if init then if init then
init(self,prop); init(self,prop);
@ -318,6 +322,18 @@ function module.init(shared)
return self; return self;
end end
function this:GetPropertyChangedSignal(propertyName)
local signal = self.__propertyChangedSignals[propertyName]
if not signal then
signal = {}
self.__propertyChangedSignals[propertyName] = signal
end
end
function this:EmitPropertyChangedSignal(propertyName,value)
end
--- re-render object (if some props chaged, call this to render again) --- re-render object (if some props chaged, call this to render again)
function this:update() -- swap object function this:update() -- swap object
local object = rawget(self,"__object"); -- get last instance local object = rawget(self,"__object"); -- get last instance

View file

@ -45,7 +45,12 @@ function module.init(id)
return this,this.round,this.class,this.mount,this.store,this.event,this.tween,this.style; return this,this.round,this.class,this.mount,this.store,this.event,this.tween,this.style;
end end
local function cleanup(space)
-- space.items
end
function module.uninit(id) function module.uninit(id)
pcall(cleanup,idSpace[id])
idSpace[id] = nil; idSpace[id] = nil;
end end

View file

@ -145,6 +145,11 @@ module.LerpProperties = LerpProperties
--Properties : 트윈할 속성과 목표값 예시 : --Properties : 트윈할 속성과 목표값 예시 :
--Data.Properties.Position = UDim2.new(1,0,1,0) 처럼 하면 Position 속성의 목표를 1,0,1,0 으로 지정 --Data.Properties.Position = UDim2.new(1,0,1,0) 처럼 하면 Position 속성의 목표를 1,0,1,0 으로 지정
function module.RunTween(Item,Data,Properties,Ended,OnStepped,Setter,Getter,_) function module.RunTween(Item,Data,Properties,Ended,OnStepped,Setter,Getter,_)
OnStepped = OnStepped or Data.OnStepped
Ended = Ended or Data.Ended
Setter = Setter or Data.Setter
Getter = Getter or Data.Getter
-- remove self -- remove self
if Item == module then warn "AdvancedTween:RunTween() is deprecated, Use AdvancedTween.RunTween() instead"; Item = Data; Data = Properties; Properties = Ended; Ended = OnStepped; OnStepped = Setter; Setter = Getter; Getter = _; end if Item == module then warn "AdvancedTween:RunTween() is deprecated, Use AdvancedTween.RunTween() instead"; Item = Data; Data = Properties; Properties = Ended; Ended = OnStepped; OnStepped = Setter; Setter = Getter; Getter = _; end
@ -275,20 +280,12 @@ function module.RunTween(Item,Data,Properties,Ended,OnStepped,Setter,Getter,_)
if CallBack then if CallBack then
for FncIndex,Fnc in pairs(CallBack) do for FncIndex,Fnc in pairs(CallBack) do
if FncIndex == "*" then if FncIndex == "*" then
Fnc(Index,Alpha,Item) Fnc(Item,Index,Alpha)
else else
local num = tonumber(FncIndex) local num = tonumber(FncIndex)
if num then if num and num <= Index then
if num <= Index then Fnc(Alpha,Index,Item)
Fnc(Alpha,Item) CallBack[FncIndex] = nil
CallBack[FncIndex] = nil
end
else
local alphaNum = tonumber(FncIndex:match"~([%d.]+)")
if alphaNum <= Alpha then
Fnc(Index,Item)
CallBack[FncIndex] = nil
end
end end
end end
end end

19
src/signal.lua Normal file
View file

@ -0,0 +1,19 @@
local module = {}
local signal
local customSignal = {}
customSignal.__index = customSignal
function customSignal:emit(name,...)
end
function customSignal:Connect()
end
function customSignal.new()
local self = {}
setmetatable(self,customSignal)
end
function this.new(...)
customSignal.new(...)
end
this.customSignal = customSignal

View file

@ -5,11 +5,12 @@ this feature allows get object without making some created callback and local va
but, it can't allows mulit id and object but, it can't allows mulit id and object
this feature should be upgraded this feature should be upgraded
]] ]]
local wrap = coroutine.wrap; local wrap = coroutine.wrap;
local insert = table.insert; local insert = table.insert;
local remove = table.remove; local remove = table.remove;
local gmatch = string.gmatch; local gmatch = string.gmatch;
local gsub = string.gsub; local gsub = string.gsub;
local match = string.match;
local function catch(...) local function catch(...)
local passed,err = pcall(...); local passed,err = pcall(...);
@ -50,12 +51,11 @@ function module.init(shared)
function objectListClass:remove(indexOrItem) function objectListClass:remove(indexOrItem)
local thisType = type(indexOrItem); local thisType = type(indexOrItem);
if thisType == "number" then if thisType == "number" then
remove(self,indexOrItem); return remove(self,indexOrItem),indexOrItem;
else else
for i,v in pairs(self) do for i,v in pairs(self) do
if v == indexOrItem then if v == indexOrItem then
remove(self,i); return remove(self,i),i;
break;
end end
end end
end end
@ -76,12 +76,26 @@ function module.init(shared)
objectListClass.__index = objectListClass; objectListClass.__index = objectListClass;
-- get object array with id (objSpace) -- get object array with id (objSpace)
function new.getObjects(id) function new.getObjects(ids)
local list = items[id]; if match(ids,",") then
if list then return list; end local list = items[ids];
list = objectListClass.__new(id); if list then return list; end
items[id] = list; list = objectListClass.__new();
return list; items[ids] = list;
return list;
else
local list = objectListClass.__new();
for id in gmatch(ids,"[^,]+") do -- split by ,
id = gsub(gsub(id,"^ +","")," +$","");
local idItem = items[id];
if idItem then
for _,item in pairs(idItem) do
insert(list,item);
end
end
end
return list
end
end end
-- get first object with id (not array) -- get first object with id (not array)
function new.getObject(id) function new.getObject(id)
@ -208,7 +222,7 @@ function module.init(shared)
-- if got register, just copy data to self and connect -- if got register, just copy data to self and connect
if type(value) == "table" and value.__type == "quad_register" then if type(value) == "table" and value.__type == "quad_register" then
-- warn "[Quad] adding register value on store is only allowed when init store. set value request was ignored"; -- warn "[Quad] adding register value on store is only allowed when init store. set value request was ignored";
local selfValues = self.__self; local selfValues = self.__self;
local selfTweens = self.__tweens; local selfTweens = self.__tweens;
@ -303,8 +317,7 @@ function module.init(shared)
return register; return register;
end end
function store:default(key,value) function store:default(key,value)
local old = self[key]; if self[key] == nil then
if old == nil then
self[key] = value; self[key] = value;
return; return;
end end

165
src/types.lua Normal file
View file

@ -0,0 +1,165 @@
-------------------
-- module_class
-------------------
export type extend = {
getter: {[string]: ()->any|any?};
setter: {[string]: ()->()?};
}
export type DOM = {
[string]: any;
}
export type DOM_constructor = {
[event]:
(DOM,...any)->()
&{self: any,func: ()->()};
} & { [number]: DOM|style; }
& { [string]: any|register; }
export type DOM_creator = (DOM_constructor,...DOM_constructor)->DOM
export type imported =
{[string]:any}
&(ids:ObjectIdList)->DOM_creator
&DOM_creator
export type import = (ClassName:string|ModuleScript|extend|()->()|{any},defaultProperties:DOM_constructor?)->imported
export type module_class = {
extend: ()->extend;
import: import;
getProperty: (item:extend|any,index:string,ClassName:string?)->any;
setProperty: (item:extend|any,index:string,value:any,ClassName:string?)->();
make: (ClassName:string|(...any)->any|extend,...{any})->any;
} & import
-------------------
-- module_event
-------------------
export type event = string
export type disconnecter = {
add: (self:disconnecter,connection:RBXScriptConnection)->();
destroy: (self:disconnecter)->();
disconnect: (self:disconnecter)->();
}
export type module_event = {
prop: (propName:string)->event;
createdAsync: event;
created: event;
bind: (this:DOM|any,key:event|string,func:(...any)->(),typefunc:string?)->();
disconnecter: (id:string?)->disconnecter;
} & (eventName:string)->event;
-------------------
-- module_signal
-------------------
export type module_signal = {}
-------------------
-- module_register
-------------------
export type register = {
register: (self:register,()->())->();
with: <R>(self:R&register,handler:{any}|(store:store,value:any,key:any,item:DOM)->any)->R&register;
default: <R>(self:R&register,value:any)->R&register;
add: <R>(self:R&register,value:any)->R&register;
tween: <R>(self:R&register,tween:TweenOptions)->R&register;
}
export type store = {}
export type objectList = {
each: (self:objectList,(item:DOM,index:number)->())->();
eachSync: (self:objectList,(item:DOM,index:number)->())->();
remove: (self:objectList,index:number|DOM)->(DOM?,number?);
isEmpty: (self:objectList)->boolean;
}
export type ObjectIdList = string
export type module_store = {
getObjects: (ids:ObjectIdList)->objectList;
getObject: (id:string)->DOM?;
addObject: (ids:ObjectIdList)->();
}
-------------------
-- module_signal
-------------------
export type style = {}
export type module_style = {}
-------------------
-- module_signal
-------------------
export type module_mount = {}
-------------------
-- module_signal
-------------------
export type TweenOnStepped = (Item:DOM|any,Alpha:number,AbsolutePercent:number)->()
export type TweenEnded = (Item:DOM|any)->()
export type TweenSetter = (Item:DOM|any,Property:string,Value:Lerpable)->()
export type TweenGetter = (Item:DOM|any,Property:string)->()
export type TweenOptions = {
Easing: EasingFunction?;
Direction: EasingDirection?;
CallBack: {[number|"*"|string]:(Item:DOM|any,Alpha:number,AbsolutePercent:number)->()}?;
OnStepped: TweenOnStepped?; -- Same as CallBack{["*"]:()->()} But faster then CallBack due to table loop
Ended: TweenEnded?;
Getter: TweenGetter?;
Setter: TweenSetter?;
}
export type EasingFunction = {run:(number)->number,[any]:any}
export type EasingFunctions = {
Linear: EasingFunction; ---직선, Linear. i=x, x=0 ~ 1
Quint: EasingFunction; ---5제곱, Quint. (^5) i=1-(1-x)^5, x=0 ~ 1
Quart: EasingFunction; ---4제곱, Quart. (^4) i=1-(1-x)^4, x=0 ~ 1
Cubic: EasingFunction; ---3제곱, Cubic. (^3) i=1-(1-x)^3, x=0 ~ 1
Quad: EasingFunction; ---2제곱, Quad. (^2) i=1-(1-x)^2, x=0 ~ 1
Sin: EasingFunction; ---사인파, Sin. i=sin(x*pi/2), x=0 ~ 1
Circle: EasingFunction; ---사분원, Circle. i=sqrt(1-(1-x)^2), x=0 ~ 1
Expo: EasingFunction; ---지수함수, Expo. i=1-2^(-10*x), x=0~1
Elastic: EasingFunction; ---튀어오름, Elastic.
Bounce: EasingFunction; ---통통거림, Bounce
-- Old things
Exp2: EasingFunction; ---덜 가파른 지수. i=math.exp(x), x=-4 ~ 2
Exp4: EasingFunction; ---더 가파른 지수. i=math.exp(x), x=-4 ~ 4
Exp2Max4: EasingFunction; ---@deprecated
}
export type EasingDirection = string
export type EasingDirections = {
Out: EasingDirection&"Out";
In: EasingDirection&"In";
}
export type Lerpable = Color3|UDim|UDim2|number|Vector2|Vector3|CFrame
export type TweenHandler = ()->();
export type AdvancedTween = {
EasingFunctions:EasingFunctions;
EasingDirections:EasingDirections;
LerpProperties: <item>(item:item&(DOM|any),old:{[string]:Lerpable},new:{[string]:Lerpable},alpha:number,setter:(item:item&(DOM|any),property:string,value:Lerpable)->()?)->();
RunTween: (Item:DOM|any,Option:TweenOptions,Properties:{[string]:Lerpable},Ended:TweenEnded?,OnStepped:TweenOnStepped?,Setter:TweenSetter?,Getter:TweenGetter?)->TweenHandler;
}
-------------------
-- module_signal
-------------------
export type round = {
setRound: (ImageFrame:ImageLabel|ImageButton,RoundSize:number)->(ImageLabel|ImageButton);
setOutline: (ImageFrame:ImageLabel|ImageButton,RoundSize:number)->(ImageLabel|ImageButton);
getRound: (ImageFrame:ImageLabel|ImageButton)->number;
getOutline: (ImageFrame:ImageLabel|ImageButton)->number;
}
-------------------
-- module
-------------------
export type module_exported = {
round: round;
tween: AdvancedTween;
style: module_style;
event: module_event;
store: module_store;
mount: module_mount;
class: module_class;
}
export type module = {
uninit: (id:string)->();
init: (id:string)->module_exported;
}
return {}

11
src/vercheck.lua Normal file
View file

@ -0,0 +1,11 @@
local IS_TEST = true
local VER = "1.14" .. (IS_TEST and "B" or "")
if IS_TEST then
warn("You are using BETA version of quad now. Many features may change in the future and unstable. AS USING BETA VERSION OF QUAD, YOU SHOULD KNOW IT WILL BUGGY SOMETIME. still on development - you can ignore this message if have no issue. if you have issue on using quad, please report issue on github. VERSION: "..VER)
end
return {
version = VER
}