diff options
author | Joe Crayne <joe@jerkface.net> | 2019-05-24 21:11:14 -0400 |
---|---|---|
committer | Joe Crayne <joe@jerkface.net> | 2019-05-24 21:11:14 -0400 |
commit | 786e58ccbb05ced78c5421b53fbc469971d7db82 (patch) | |
tree | 0c60c0bbfd357c3d21d849dd61ecfb50d7ac1cc7 | |
parent | a2aa65ffc5a4fc6cd0f41ccab1516f85a27989b2 (diff) |
Add curvature-coloring.
-rw-r--r-- | MeshSketch.hs | 24 | ||||
-rw-r--r-- | PointPrimitiveRing.hs | 7 | ||||
-rw-r--r-- | SmallRing.hs | 39 |
3 files changed, 65 insertions, 5 deletions
diff --git a/MeshSketch.hs b/MeshSketch.hs index 8df74b3..ea8fbe6 100644 --- a/MeshSketch.hs +++ b/MeshSketch.hs | |||
@@ -60,6 +60,7 @@ import MtlParser (ObjMaterial(..)) | |||
60 | import Matrix | 60 | import Matrix |
61 | import PointPrimitiveRing | 61 | import PointPrimitiveRing |
62 | import MaskableStream (AttributeKey,(@<-)) | 62 | import MaskableStream (AttributeKey,(@<-)) |
63 | import SmallRing | ||
63 | 64 | ||
64 | 65 | ||
65 | prettyDebug :: GL.DebugMessage -> String | 66 | prettyDebug :: GL.DebugMessage -> String |
@@ -105,6 +106,7 @@ data State = State | |||
105 | , stPenDown :: IORef Bool | 106 | , stPenDown :: IORef Bool |
106 | , stPlane :: IORef (Maybe Plane) | 107 | , stPlane :: IORef (Maybe Plane) |
107 | , stDragPlane :: IORef (Maybe (Vector Float,Plane)) | 108 | , stDragPlane :: IORef (Maybe (Vector Float,Plane)) |
109 | , stRecentPts :: IORef (Giver (Vector Double)) | ||
108 | } | 110 | } |
109 | 111 | ||
110 | data Camera = Camera | 112 | data Camera = Camera |
@@ -229,6 +231,7 @@ uploadState obj glarea storage = do | |||
229 | dragPlane <- newIORef Nothing | 231 | dragPlane <- newIORef Nothing |
230 | pendown <- newIORef False | 232 | pendown <- newIORef False |
231 | plane <- newIORef $ Just (xzPlaneVector G.// [(3,-1)]) | 233 | plane <- newIORef $ Just (xzPlaneVector G.// [(3,-1)]) |
234 | recentPts <- newIORef Give0 | ||
232 | 235 | ||
233 | let st = State | 236 | let st = State |
234 | { stAnimator = tm | 237 | { stAnimator = tm |
@@ -242,6 +245,7 @@ uploadState obj glarea storage = do | |||
242 | , stPenDown = pendown | 245 | , stPenDown = pendown |
243 | , stPlane = plane | 246 | , stPlane = plane |
244 | , stDragPlane = dragPlane | 247 | , stDragPlane = dragPlane |
248 | , stRecentPts = recentPts | ||
245 | } | 249 | } |
246 | -- _ <- addAnimation tm (whirlingCamera st) | 250 | -- _ <- addAnimation tm (whirlingCamera st) |
247 | 251 | ||
@@ -615,14 +619,23 @@ pushRing w st h k c = do | |||
615 | plane <- readIORef (stPlane st) | 619 | plane <- readIORef (stPlane st) |
616 | d <- worldCoordinates st h k plane | 620 | d <- worldCoordinates st h k plane |
617 | Just win <- getWidgetWindow w | 621 | Just win <- getWidgetWindow w |
622 | g <- pushFront (fromList [h,k]) <$> readIORef (stRecentPts st) | ||
623 | writeIORef (stRecentPts st) g | ||
624 | with3 g $ \a b c -> do | ||
625 | let d = det $ fromRows [(b-c),(a-b)] | ||
626 | putStrLn $ "d = " ++ show d | ||
627 | updateBack (stRingBuffer st) $ \RingPoint{..} -> do | ||
628 | rpColor @<- if d<0 then blue else red | ||
618 | pushBack (stRingBuffer st) $ \RingPoint{..} -> do | 629 | pushBack (stRingBuffer st) $ \RingPoint{..} -> do |
619 | rpPosition @<- d | 630 | rpPosition @<- d |
620 | rpColor @<- c | 631 | rpColor @<- c |
621 | windowInvalidateRect win Nothing False | 632 | windowInvalidateRect win Nothing False |
622 | return d | 633 | return d |
623 | 634 | ||
624 | yellow = fromList [1,1,0] :: Vector Float | 635 | red,yellow,blue :: Vector Float |
625 | red = fromList [1,0,0] :: Vector Float | 636 | yellow = fromList [1,1,0] |
637 | blue = fromList [0,0,1] | ||
638 | red = fromList [1,0,0] | ||
626 | 639 | ||
627 | onEvent :: IsWidget w => w -> Realized -> Event -> IO Bool | 640 | onEvent :: IsWidget w => w -> Realized -> Event -> IO Bool |
628 | onEvent w realized ev = do | 641 | onEvent w realized ev = do |
@@ -646,8 +659,11 @@ onEvent w realized ev = do | |||
646 | Just InputSourcePen -> do | 659 | Just InputSourcePen -> do |
647 | isDown <- readIORef (stPenDown st) | 660 | isDown <- readIORef (stPenDown st) |
648 | when isDown $ do | 661 | when isDown $ do |
649 | d <- pushRing w st h k yellow | 662 | -- TODO: Read prior two points and example the angle. |
650 | put (etype,(h,k),d) | 663 | -- If it is small, reclassify the prior point. |
664 | d <- pushRing w st h k blue | ||
665 | -- put (etype,(h,k),d) | ||
666 | return () | ||
651 | _ -> do | 667 | _ -> do |
652 | -- put (h,k) | 668 | -- put (h,k) |
653 | updateCameraRotation w st h k | 669 | updateCameraRotation w st h k |
diff --git a/PointPrimitiveRing.hs b/PointPrimitiveRing.hs index 3647d4a..c458421 100644 --- a/PointPrimitiveRing.hs +++ b/PointPrimitiveRing.hs | |||
@@ -81,7 +81,7 @@ updateRingCommands r = do | |||
81 | front | front > cnt -> [(front - cnt,size)] | 81 | front | front > cnt -> [(front - cnt,size)] |
82 | | otherwise -> [(0,back), (front,cnt - front)] | 82 | | otherwise -> [(0,back), (front,cnt - front)] |
83 | updateCommands (rStorage r) (rObject r) mask | 83 | updateCommands (rStorage r) (rObject r) mask |
84 | readIORef (objCommands $ rObject r) >>= mapM_ print | 84 | -- readIORef (objCommands $ rObject r) >>= mapM_ print |
85 | return () | 85 | return () |
86 | 86 | ||
87 | pushBack :: Ring keys -> (keys -> Writer [DSum AttributeKey GLUniformValue] a) -> IO () | 87 | pushBack :: Ring keys -> (keys -> Writer [DSum AttributeKey GLUniformValue] a) -> IO () |
@@ -93,5 +93,10 @@ pushBack r attrs = do | |||
93 | when (sz < ringCapacity r) $ writeIORef (rSize r) (sz + 1) | 93 | when (sz < ringCapacity r) $ writeIORef (rSize r) (sz + 1) |
94 | updateRingCommands r | 94 | updateRingCommands r |
95 | 95 | ||
96 | updateBack :: Ring keys -> (keys -> Writer [DSum AttributeKey GLUniformValue] a) -> IO () | ||
97 | updateBack r attrs = do | ||
98 | back <- readIORef $ rBack r | ||
99 | updateAttributes (mod (back - 1) (ringCapacity r)) $ attrs (rKeys r) | ||
100 | |||
96 | updateRingUniforms :: GLStorage -> Ring keys -> IO () | 101 | updateRingUniforms :: GLStorage -> Ring keys -> IO () |
97 | updateRingUniforms _ _ = return () | 102 | updateRingUniforms _ _ = return () |
diff --git a/SmallRing.hs b/SmallRing.hs new file mode 100644 index 0000000..d792899 --- /dev/null +++ b/SmallRing.hs | |||
@@ -0,0 +1,39 @@ | |||
1 | {-# LANGUAGE RankNTypes #-} | ||
2 | module SmallRing where | ||
3 | |||
4 | import Data.Ratio | ||
5 | |||
6 | odds :: (Integral i, Num a) => i -> [a] | ||
7 | odds x = [ 1 + 2 * fromIntegral n | n <- [0..x] ] | ||
8 | |||
9 | pts :: (Fractional a, Integral b) => b -> [a] | ||
10 | pts i = let d = 2^i in [ k / d | k <- odds (2^(i-1) - 1) ] | ||
11 | |||
12 | fractions :: Fractional b => [b] | ||
13 | fractions = concatMap pts [1..] | ||
14 | |||
15 | vis :: Int -> Ratio Int -> [Char] | ||
16 | vis w α = let i = numerator α | ||
17 | n = denominator α | ||
18 | x = (w * i) `div` n | ||
19 | in replicate (x-1) '.' ++ "x" ++ replicate (w-max x 1) '.' ++ show α | ||
20 | |||
21 | data Giver a | ||
22 | = Give0 | ||
23 | | Give1 (forall b. (a -> b) -> b) | ||
24 | | Give2 (forall b. (a -> a -> b) -> b) | ||
25 | | Give3 (forall b. (a -> a -> a -> b) -> b) | ||
26 | |||
27 | pushFront :: a -> Giver a -> Giver a | ||
28 | pushFront a Give0 = Give1 ($ a) | ||
29 | pushFront a (Give1 f) = Give2 (\g -> f (g a)) | ||
30 | pushFront a (Give2 f) = Give3 (\g -> f (g a)) | ||
31 | pushFront a (Give3 f) = f $ \b c _ -> Give3 $ \g -> g a b c | ||
32 | |||
33 | take3 :: (a -> a -> a -> b) -> Giver a -> Maybe b | ||
34 | take3 f (Give3 g) = Just (g f) | ||
35 | take3 _ _ = Nothing | ||
36 | |||
37 | with3 :: Applicative f => Giver a -> (a -> a -> a -> f ()) -> f () | ||
38 | with3 (Give3 g) f = g f | ||
39 | with3 _ _ = pure () | ||